Сделайте LocalTime
начала и остановки.
Добавьте час к началу.
LocalTime lt = start.plusHours( 1 ) ;
Обратите внимание на неизменяемые объекты. Вместо того, чтобы изменять исходный объект, мы получаем объект fre sh new LocalTime
.
Сравните с остановкой, вызвав методы isBefore
, isAfter
и isEqual
. Если еще не прошло, добавьте еще час. Если вы проходите мимо остановки, то используйте саму остановку, а не следующий час.
Собрать в List < LocalTime>
.
Если вы хотите отслеживать каждую запись как пару объектов LocalTime
, определите класс с именем что-то вроде TimeSlot
с парой LocalTime
поля участника. Здесь отлично подойдет новая функция Records , предварительно просмотренная в Java 14.
Все это уже много раз освещалось в переполнении стека. Поиск, чтобы узнать больше.
Пример приложения
Вот пример рабочего приложения. При этом используется новая функция Records
, определенная в JEP 359: записи (предварительный просмотр) , предварительный просмотр в Java 14, работа в IntelliJ 2020.1 IDE.
package work.basil.example;
import java.time.Duration;
import java.time.LocalTime;
public record LocalTimeRange(LocalTime start , LocalTime stop)
{
}
Мы можем немного представить себе это.
Мы переопределяем toString
, чтобы создать текст в одном из четырех стандартных форматов ISO 8601: ЧЧ: ММ / ЧЧ: ММ. Мы определяем перечисление для четырех типов форматов, определенных ISO 8601 для временных интервалов . Наш метод format
использует один из этих флагов для создания текста в одном из четырех стандартных форматов.
Мы производим объект Duration
по запросу. Этот класс представляет промежуток времени, не привязанный к временной шкале в масштабе часов, минут и секунд.
Поскольку это record
, нам не нужно переопределять equals
& hashCode
. Нам также не нужны методы получения для частей начального и конечного LocalTime
объектов.
package work.basil.example;
import java.time.Duration;
import java.time.LocalTime;
public record LocalTimeRange(LocalTime start , LocalTime end)
{
public enum Format
{ START_AND_END, START_AND_DURATION, DURATION_AND_END, DURATION_ONLY } // Per ISO 8601 standard.
@Override
public String toString ( ) { return this.format( Format.START_AND_END ); } // Per ISO 8601 standard.
public Duration toDuration ( ) { return Duration.between( this.start , this.end ); }
public String format ( LocalTimeRange.Format format )
{
return switch ( format )
{
case START_AND_END -> this.start + "/" + this.end;
case START_AND_DURATION -> this.start.toString() + "/" + this.toDuration().toString();
case DURATION_AND_END -> this.toDuration().toString() + "/" + this.end.toString();
case DURATION_ONLY -> this.toDuration().toString();
};
}
}
Нам нужен метод для создания часовых диапазонов времени.
private List < LocalTimeRange > hourlyRanges ( final LocalTime start , final LocalTime stop )
{
// Verify arguments
Objects.requireNonNull( start , "Received null time-of-day for start. Message # 51521a5c-5f49-4c74-98e3-fce2587edf77." );
Objects.requireNonNull( stop , "Received null time-of-day for stop. Message # 41b98429-4edb-4209-a12f-e266dcae4a90." );
// Logic
int initialCapacity = java.lang.Math.toIntExact( Duration.between( start , stop ).toHours() + 1 ); // Returns the value of the long argument; throwing an exception if the value overflows an int.
ArrayList < LocalTimeRange > ranges = new ArrayList <>( initialCapacity );
LocalTime localTime = start;
while ( ! localTime.isAfter( stop ) )
{
LocalTimeRange range = null;
LocalTime hourLater = localTime.plusHours( 1 );
if ( ! hourLater.isAfter( stop ) )
{
range = new LocalTimeRange( localTime , hourLater );
} else
{
range = new LocalTimeRange( localTime , stop );
}
Objects.requireNonNull( range );
ranges.add( range );
// Prepare for next loop.
localTime = hourLater;
}
ranges.trimToSize();
return Objects.requireNonNull( ranges );
}
И некоторый код для его применения.
LocalTime start = LocalTime.parse( "10:00:00" );
LocalTime end = LocalTime.parse( "20:30:00" );
List < LocalTimeRange > ranges = this.hourlyRanges( start , end );
System.out.println( "ranges = " + ranges );
System.out.println( ranges.stream().map( range -> range.toDuration() ).collect( Collectors.toList() ) );
System.out.println( ranges.stream().map( range -> range.format( LocalTimeRange.Format.START_AND_END ) ).collect( Collectors.toList() ) );
System.out.println( ranges.stream().map( range -> range.format( LocalTimeRange.Format.START_AND_DURATION ) ).collect( Collectors.toList() ) );
System.out.println( ranges.stream().map( range -> range.format( LocalTimeRange.Format.DURATION_AND_END ) ).collect( Collectors.toList() ) );
System.out.println( ranges.stream().map( range -> range.format( LocalTimeRange.Format.DURATION_ONLY ) ).collect( Collectors.toList() ) );
При запуске:
диапазоны = [10: 00/11: 00, 11: 00/12: 00, 12: 00/13: 00, 13: 00/14: 00, 14: 00/15: 00, 15: 00/16: 00, 16: 00/17: 00, 17: 00/18: 00, 18: 00/19: 00, 19: 00/20: 00, 20: 00/20: 30]
[PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT30M]
[10: 00/11: 00, 11: 00/12: 00, 12: 00/13: 00, 13: 00/14: 00, 14: 00/15: 00, 15: 00/16: 00, 16: 00/17: 00, 17: 00/18: 00, 18: 00/19: 00, 19: 00/20: 00, 20: 00/20: 30]
[10:00 / PT1H, 11:00 / PT1H, 12: 00 / PT1H, 13:00 / PT1H, 14: 00 / PT1H, 15: 00 / PT1H, 16: 00 / PT1H, 17: 00 / PT1H, 18: 00 / PT1H, 19: 00 / PT1H, 20: 00 / PT30M]
[PT1H / 11: 00, PT1H / 12: 00, PT1H / 13: 00, PT1H / 14: 00, PT1H / 15: 00, PT1H / 16: 00, PT1H / 17: 00, PT1H / 18: 00, PT1H / 19: 00, PT1H / 20: 00, PT30M / 20: 30]
[PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT1H, PT30M]
О java .time
java .time фреймворк встроен в Java 8 и более поздние версии. Эти классы вытесняют проблемные старые устаревшие классы даты и времени, такие как java.util.Date
, Calendar
, & SimpleDateFormat
.
Чтобы узнать больше, см. Учебник Oracle . И поиск переполнения стека для многих примеров и объяснений. Спецификация: JSR 310 .
Проект Joda-Time , теперь в режиме обслуживания , рекомендует перейти на java .time классы.
Вы можете обмениваться java .time объектами непосредственно с вашей базой данных. Используйте JDB C драйвер , совместимый с JDB C 4.2 или более поздней версией. Нет необходимости в строках, нет необходимости в java.sql.*
классах. Поддержка Hibernate 5 и JPA 2.2 java .time .
Где взять java .time классы?
