Jak uzyskać godzinę rozpoczęcia i zakończenia dnia?

121

Jak uzyskać godzinę rozpoczęcia i zakończenia dnia?

taki kod nie jest dokładny:

 private Date getStartOfDay(Date date) {
    Calendar calendar = Calendar.getInstance();
    int year = calendar.get(Calendar.YEAR);
    int month = calendar.get(Calendar.MONTH);
    int day = calendar.get(Calendar.DATE);
    calendar.set(year, month, day, 0, 0, 0);
    return calendar.getTime();
}

private Date getEndOfDay(Date date) {
    Calendar calendar = Calendar.getInstance();
    int year = calendar.get(Calendar.YEAR);
    int month = calendar.get(Calendar.MONTH);
    int day = calendar.get(Calendar.DATE);
    calendar.set(year, month, day, 23, 59, 59);
    return calendar.getTime();
}

Nie jest dokładna co do milisekundy.

kalman03
źródło
8
Co masz na myśli, mówiąc, że to „niedokładne”?
Kirk Woll,
Co jest nie tak z kodem? Co otrzymujesz, czego się nie spodziewasz? W jakiej strefie czasowej chcesz rozpocząć i zakończyć swoje dni?
Mark Reed,
4
Powyższy kod nie wykorzystuje nawet daty przekazanej do metody. Powinno działać: calendar.setTime (data) po utworzeniu kalendarza.
Jerry Destremps
2
To pytanie zakłada, że ​​wartości daty i godziny mają rozdzielczość milisekund. Prawda dla java.util.Date i Joda-Time. Ale Fałsz dla pakietu java.time w Javie 8 (nanosekund), niektórych baz danych, takich jak Postgres (mikrosekundy), bibliotek uniksowych (całe sekundy) i być może innych. Zobacz moją odpowiedź na bezpieczniejsze podejście przy użyciu Half-Open.
Basil Bourque,
2
Właściwie powinieneś otrzymać początek następnego dnia i podczas iteracji elementów w tym dniu (zakładając, że chcesz to zrobić), określisz górną granicę za pomocą <zamiast <=. To wykluczałoby następny dzień, ale obejmowałoby cały poprzedni dzień z dokładnością do nanosekundy.
Daniel F

Odpowiedzi:

115

tl; dr

LocalDate                       // Represents an entire day, without time-of-day and without time zone.
.now(                           // Capture the current date.
    ZoneId.of( "Asia/Tokyo" )   // Returns a `ZoneId` object.
)                               // Returns a `LocalDate` object.
.atStartOfDay(                  // Determines the first moment of the day as seen on that date in that time zone. Not all days start at 00:00!
    ZoneId.of( "Asia/Tokyo" ) 
)                               // Returns a `ZonedDateTime` object.

Początek dnia

Uzyskaj pełny obraz dnia dzisiejszego w strefie czasowej.

Korzystanie z podejścia Half-Open, w którym początek jest włączający, a koniec wyłączny . Takie podejście rozwiązuje lukę w kodzie, która nie uwzględnia ostatniej sekundy dnia.

ZoneId zoneId = ZoneId.of( "Africa/Tunis" ) ;
LocalDate today = LocalDate.now( zoneId  ) ;

ZonedDateTime zdtStart = today.atStartOfDay( zoneId ) ;
ZonedDateTime zdtStop = today.plusDays( 1 ).atStartOfDay( zoneId ) ;

zdtStart.toString () = 2020-01-30T00: 00 + 01: 00 [Afryka / Tunis]

zdtStop.toString () = 2020-01-31T00: 00 + 01: 00 [Afryka / Tunis]

Zobacz te same momenty w UTC.

Instant start = zdtStart.toInstant() ;
Instant stop = zdtStop.toInstant() ;

start.toString () = 2020-01-29T23: 00: 00Z

stop.toString () = 2020-01-30T23: 00: 00Z

Jeśli chcesz, aby data była wyświetlana przez cały dzień w UTC, a nie w strefie czasowej, użyj OffsetDateTime.

LocalDate today = LocalDate.now( ZoneOffset.UTC  ) ;

OffsetDateTime odtStart = today.atTime( OffsetTime.MIN ) ;
OffsetDateTime odtStop = today.plusDays( 1 ).atTime( OffsetTime.MIN ) ;

odtStart.toString () = 2020-01-30T00: 00 + 18: 00

odtStop.toString () = 2020-01-31T00: 00 + 18: 00

Te OffsetDateTime obiekty będą już w UTC, ale możesz wywołać, toInstantjeśli potrzebujesz takich obiektów, które z definicji zawsze znajdują się w UTC.

Instant start = odtStart.toInstant() ;
Instant stop = odtStop.toInstant() ;

start.toString () = 2020-01-29T06: 00: 00Z

stop.toString () = 2020-01-30T06: 00: 00Z

Wskazówka: możesz być zainteresowany dodaniem biblioteki ThreeTen-Extra do swojego projektu, aby użyć jej Intervalklasy do reprezentowania tej pary Instantobiektów. Daje to klasa użytecznych metod porównywania takich jak abuts, overlaps, containsi więcej.

Interval interval = Interval.of( start , stop ) ;

interval.toString () = 2020-01-29T06: 00: 00Z / 2020-01-30T06: 00: 00Z

Wpół otwarty

Odpowiedź przez mprivat jest poprawna. Chodzi mu o to, aby nie próbować uzyskać końca dnia, ale raczej porównać to z „przed rozpoczęciem następnego dnia”. Jego pomysł znany jest jako podejście „Half-Open”, w którym okres czasu ma początek obejmujący, a koniec wyłączny .

  • Bieżące ramy daty i czasu w Javie (java.util.Date/Calendar i Joda-Time ) używają milisekund od epoki . Jednak w Javie 8 nowe klasy JSR 310 java.time. * Używają rozdzielczości nanosekund. Każdy kod, który napisałeś w oparciu o wymuszenie liczenia milisekund ostatniej chwili dnia byłby niepoprawny, gdyby został przełączony na nowe klasy.
  • Porównywanie danych z innych źródeł staje się błędne, jeśli stosują inne rozwiązania. Na przykład biblioteki uniksowe zwykle wykorzystują całe sekundy, a bazy danych, takie jak Postgres, określają datę i godzinę na mikrosekundy.
  • Niektóre zmiany czasu letniego mają miejsce w ciągu północy, co może jeszcze bardziej zmylić sytuację.

wprowadź opis obrazu tutaj

Czas Joda- 2.3 oferuje metodę tego samego celu, do otrzymania pierwszej chwili dnia: withTimeAtStartOfDay(). Podobnie w java.time, LocalDate::atStartOfDay.

Wyszukaj w StackOverflow „joda półotwarta”, aby zobaczyć więcej dyskusji i przykładów.

Zobacz ten post, Przedziały czasowe i inne zakresy powinny być w połowie otwarte , autorstwa Billa Schneidera.

Unikaj starszych klas daty i godziny

Klasy java.util.Date i .Calendar są notorycznie kłopotliwe. Unikaj ich.

Użyj klas java.time . Java.time ramy jest oficjalnym następcą bardzo udanego Joda-Time bibliotece.

java.time

Struktura java.time jest wbudowana w Javę 8 i nowsze. Z powrotem przeniesiony do Java 6 i 7 w projekcie ThreeTen-Backport , dodatkowo dostosowany do Androida w projekcie ThreeTenABP .

Na Instantosi czasu znajduje się moment w UTC z rozdzielczością nanosekund .

Instant instant = Instant.now();

Zastosuj strefę czasową, aby uzyskać czas na zegarze ściennym dla niektórych miejscowości.

ZoneId zoneId = ZoneId.of( "America/Montreal" );
ZonedDateTime zdt = ZonedDateTime.ofInstant( instant , zoneId );

Aby uzyskać pierwszy moment dnia, przejdź przez LocalDatezajęcia i ich atStartOfDaymetodę.

ZonedDateTime zdtStart = zdt.toLocalDate().atStartOfDay( zoneId );

Korzystając z podejścia Half-Open, uzyskaj pierwszą chwilę następnego dnia.

ZonedDateTime zdtTomorrowStart = zdtStart.plusDays( 1 );

Tabela wszystkich typów dat i godzin w Javie, zarówno nowoczesnych, jak i starszych

Obecnie framework java.time nie posiada Intervalklasy opisanej poniżej dla Joda-Time. Jednak projekt ThreeTen-Extra rozszerza java.time o dodatkowe klasy. Ten projekt jest poligonem doświadczalnym dla ewentualnych przyszłych dodatków do java.time. Wśród jego klas jest Interval. Skonstruuj an Interval, przekazując parę Instantobiektów. Możemy wyodrębnić Instantz naszych ZonedDateTimeobiektów.

Interval today = Interval.of( zdtStart.toInstant() , zdtTomorrowStart.toInstant() );

Informacje o java.time

Struktura java.time jest wbudowana w Javę 8 i nowsze. Klasy te kłopotliwe zastąpić stary starszych klas Date-Time, takich jak java.util.Date, Calendar, i SimpleDateFormat.

Aby dowiedzieć się więcej, zobacz samouczek Oracle . I przeszukaj Stack Overflow, aby znaleźć wiele przykładów i wyjaśnień. Specyfikacja to JSR 310 .

Projekt Joda-Time , obecnie w trybie konserwacji , zaleca migrację do klas java.time .

Możesz wymieniać obiekty java.time bezpośrednio ze swoją bazą danych. Użyj sterownika JDBC zgodnego z JDBC 4.2 lub nowszym. Nie ma potrzeby stosowania ciągów ani java.sql.*klas. Hibernate 5 i JPA 2.2 obsługują java.time .

Skąd wziąć klasy java.time?


Joda-Time

UPDATE: Projekt Joda-Time jest teraz w trybie konserwacji i zaleca migrację do klas java.time . Zostawiam tę sekcję nietkniętą dla historii.

Joda-Time ma trzy klasy do reprezentowania okres czasu na różne sposoby: Interval, Period, i Duration. An Intervalma określony początek i koniec na osi czasu Wszechświata. To pasuje do naszej potrzeby reprezentowania „dnia”.

Nazywamy tę metodę withTimeAtStartOfDayzamiast ustawiania pory dnia na zera. Z powodu czasu letniego i innych anomalii pierwsza chwila dnia może nie nadejść 00:00:00.

Przykładowy kod wykorzystujący Joda-Time 2.3.

DateTimeZone timeZone = DateTimeZone.forID( "America/Montreal" );
DateTime now = DateTime.now( timeZone );
DateTime todayStart = now.withTimeAtStartOfDay();
DateTime tomorrowStart = now.plusDays( 1 ).withTimeAtStartOfDay();
Interval today = new Interval( todayStart, tomorrowStart );

Jeśli musisz, możesz przekonwertować plik na java.util.Date.

java.util.Date date = todayStart.toDate();
Basil Bourque
źródło
Muszę użyćLocalDateTime
user924,
170

Java 8


public static Date atStartOfDay(Date date) {
    LocalDateTime localDateTime = dateToLocalDateTime(date);
    LocalDateTime startOfDay = localDateTime.with(LocalTime.MIN);
    return localDateTimeToDate(startOfDay);
}

public static Date atEndOfDay(Date date) {
    LocalDateTime localDateTime = dateToLocalDateTime(date);
    LocalDateTime endOfDay = localDateTime.with(LocalTime.MAX);
    return localDateTimeToDate(endOfDay);
}

private static LocalDateTime dateToLocalDateTime(Date date) {
    return LocalDateTime.ofInstant(date.toInstant(), ZoneId.systemDefault());
}

private static Date localDateTimeToDate(LocalDateTime localDateTime) {
    return Date.from(localDateTime.atZone(ZoneId.systemDefault()).toInstant());
}

Aktualizacja : dodałem te dwie metody do moich klas narzędzi Java tutaj

Znajduje się w centralnym repozytorium Maven pod adresem:

<dependency>
  <groupId>com.github.rkumsher</groupId>
  <artifactId>utils</artifactId>
  <version>1.3</version>
</dependency>

Java 7 i starsze


Dzięki Apache Commons

public static Date atEndOfDay(Date date) {
    return DateUtils.addMilliseconds(DateUtils.ceiling(date, Calendar.DATE), -1);
}

public static Date atStartOfDay(Date date) {
    return DateUtils.truncate(date, Calendar.DATE);
}

Bez Apache Commons

public Date atEndOfDay(Date date) {
    Calendar calendar = Calendar.getInstance();
    calendar.setTime(date);
    calendar.set(Calendar.HOUR_OF_DAY, 23);
    calendar.set(Calendar.MINUTE, 59);
    calendar.set(Calendar.SECOND, 59);
    calendar.set(Calendar.MILLISECOND, 999);
    return calendar.getTime();
}

public Date atStartOfDay(Date date) {
    Calendar calendar = Calendar.getInstance();
    calendar.setTime(date);
    calendar.set(Calendar.HOUR_OF_DAY, 0);
    calendar.set(Calendar.MINUTE, 0);
    calendar.set(Calendar.SECOND, 0);
    calendar.set(Calendar.MILLISECOND, 0);
    return calendar.getTime();
}
RKumsher
źródło
5
Odradzam to podejście z powodu problemów związanych ze strefami czasowymi, czasem letnim itp., Którymi zajmie się biblioteka czasu taka jak Joda.
Edward Anderson
7
Myślę, że getStartOfDaypowinno być: LocalDateTime startOfDay = localDateTime.with(LocalTime.MIN);Tj. LocalTime, a nie LocalDateTime.
Konstantin Kulagin
Nie myśl o tych getEndOfDay(Date date). getStartOfDay(Date date)metody w sekcji Java 8 są poprawne, a mianowicie LocalDateTime.MAX i .MIN podają najwcześniejszą możliwą datę w przeszłości i w przyszłości, a nie początek i koniec dnia. Zamiast tego sugerowałbym .atStartOfDay () na początek i .plusDays (1) .atStartOfDay (). MinusNanos (1) na koniec.
Glen Mazza
Metoda localDateTimeToDate(LocalDateTime startOfDay)zgłasza wyjątek - java.lang.IllegalArgumentException: java.lang.ArithmeticException: long overflow
sanluck
1
@GlenMazza rozwiązanie Java 8 wykorzystuje Localtime .max , nie LocalDateTime.MAX . Rozwiązanie jest poprawne.
Frederico Pantuzza
28

w getEndOfDay możesz dodać:

calendar.set(Calendar.MILLISECOND, 999);

Chociaż mówiąc matematycznie, nie możesz określić końca dnia inaczej niż mówiąc, że jest to „przed początkiem następnego dnia”.

Więc zamiast mówić, if(date >= getStartOfDay(today) && date <= getEndOfDay(today))powinieneś powiedzieć: if(date >= getStartOfDay(today) && date < getStartOfDay(tomorrow)). To znacznie bardziej solidna definicja (i nie musisz się martwić o dokładność milisekund).

mprivat
źródło
1
Druga połowa tej odpowiedzi to najlepszy sposób. Takie podejście jest znane jako „Half-Open”. Wyjaśniam dalej w mojej odpowiedzi .
Basil Bourque,
14

java.time

Korzystanie z java.timeframeworka wbudowanego w Javę 8.

import java.time.LocalTime;
import java.time.LocalDateTime;

LocalDateTime now = LocalDateTime.now(); // 2015-11-19T19:42:19.224
// start of a day
now.with(LocalTime.MIN); // 2015-11-19T00:00
now.with(LocalTime.MIDNIGHT); // 2015-11-19T00:00
// end of a day
now.with(LocalTime.MAX); // 2015-11-19T23:59:59.999999999
Przemek
źródło
3
Ta odpowiedź ignoruje anomalie, takie jak czas letni (DST). Te Local…zajęcia nie mają pojęcia stref czasowych oraz dostosowanie do anomalii. Na przykład w niektórych strefach czasowych o północy następuje zmiana czasu letniego, więc pierwsza pora dnia przypada o godzinie 01:00:00.01:00, a nie o godzinie określonej 00:00:00.0przez ten kod. Użyj ZonedDateTimezamiast tego.
Basil Bourque
4

Dodatkowym sposobem znalezienia początku dnia za pomocą java8 java.time.ZonedDateTime zamiast przechodzenia przez nie LocalDateTimejest po prostu obcięcie wejścia ZonedDateTime do DAYS:

zonedDateTimeInstance.truncatedTo( ChronoUnit.DAYS );
Laur
źródło
2

W przypadku języka Java 8 działają następujące instrukcje jednowierszowe. W tym przykładzie używam strefy czasowej UTC. Rozważ zmianę aktualnie używanej strefy czasowej.

System.out.println(new Date());

final LocalDateTime endOfDay       = LocalDateTime.of(LocalDate.now(), LocalTime.MAX);
final Date          endOfDayAsDate = Date.from(endOfDay.toInstant(ZoneOffset.UTC));

System.out.println(endOfDayAsDate);

final LocalDateTime startOfDay       = LocalDateTime.of(LocalDate.now(), LocalTime.MIN);
final Date          startOfDayAsDate = Date.from(startOfDay.toInstant(ZoneOffset.UTC));

System.out.println(startOfDayAsDate);

Jeśli nie ma różnicy czasu z wyjściem. Próbować:ZoneOffset.ofHours(0)

Fırat KÜÇÜK
źródło
1
W jaki sposób wnosi to wartość większą niż istniejące odpowiedzi? Ignorujesz również kluczową kwestię strefy czasowej. A przekazywanie stałej UTC do toInstantjest nielegalną składnią i koncepcyjnie zbędne.
Basil Bourque
@BasilBourque "W jaki sposób to zwiększa wartość poza istniejącymi rozwiązaniami Answers?" Tak działa stackoverflow. A tak przy okazji, to tylko szablon. Ludzie mogą zmienić sposób, w jaki chcą. przekazanie UTC do natychmiastowego jest całkowicie legalne, możesz sprawdzić dane wyjściowe.
Fırat KÜÇÜK
2

Java 8 lub ThreeTenABP

ZonedDateTime

ZonedDateTime curDate = ZonedDateTime.now();

public ZonedDateTime startOfDay() {
    return curDate
    .toLocalDate()
    .atStartOfDay()
    .atZone(curDate.getZone())
    .withEarlierOffsetAtOverlap();
}

public ZonedDateTime endOfDay() {

    ZonedDateTime startOfTomorrow =
        curDate
        .toLocalDate()
        .plusDays(1)
        .atStartOfDay()
        .atZone(curDate.getZone())
        .withEarlierOffsetAtOverlap();

    return startOfTomorrow.minusSeconds(1);
}

// based on https://stackoverflow.com/a/29145886/1658268

LocalDateTime

LocalDateTime curDate = LocalDateTime.now();

public LocalDateTime startOfDay() {
    return curDate.atStartOfDay();
}

public LocalDateTime endOfDay() {
    return startOfTomorrow.atTime(LocalTime.MAX);  //23:59:59.999999999;
}

// based on https://stackoverflow.com/a/36408726/1658268

Mam nadzieję, że to komuś pomoże.

SudoPlz
źródło
Metoda „atTime” jest bardzo dobrym podejściem w połączeniu ze stałą „LocalTime.MAX” na koniec dnia. Miły!
Pan Anderson
2

Wypróbowałem ten kod i działa dobrze!

final ZonedDateTime now = ZonedDateTime.now(ZoneOffset.UTC);
final ZonedDateTime startofDay =
    now.toLocalDate().atStartOfDay(ZoneOffset.UTC);
final ZonedDateTime endOfDay =
    now.toLocalDate().atTime(LocalTime.MAX).atZone(ZoneOffset.UTC);
Siddhey Sankhe
źródło
Jeśli masz ZonedDateTimei Instantmasz do dyspozycji, nie musisz nigdy go używać java.sql.Timestamp. Ta klasa jest jedną z okropnych klas starszych, obecnie wypieranych przez klasy java.time . Od wersji JDBC 4.2 możemy bezpośrednio wymieniać obiekty java.time z bazą danych. Twoje mieszanie klas tradycyjnych i nowoczesnych nie ma dla mnie sensu.
Basil Bourque
1

Innym rozwiązaniem niezależnym od frameworka jest:

static public Date getStartOfADay(Date day) {
    final long oneDayInMillis = 24 * 60 * 60 * 1000;
    return new Date(day.getTime() / oneDayInMillis * oneDayInMillis);
}

static public Date getEndOfADay(Date day) {
    final long oneDayInMillis = 24 * 60 * 60 * 1000;
    return new Date((day.getTime() / oneDayInMillis + 1) * oneDayInMillis - 1);
}

Zauważ, że zwraca czas oparty na UTC

Alexander Chingarev
źródło
1
private Date getStartOfDay(Date date) {
    Calendar calendar = Calendar.getInstance();
    int year = calendar.get(Calendar.YEAR);
    int month = calendar.get(Calendar.MONTH);
    int day = calendar.get(Calendar.DATE);
    calendar.setTimeInMillis(0);
    calendar.set(year, month, day, 0, 0, 0);
    return calendar.getTime();
    }

private Date getEndOfDay(Date date) {
    Calendar calendar = Calendar.getInstance();
    int year = calendar.get(Calendar.YEAR);
    int month = calendar.get(Calendar.MONTH);
    int day = calendar.get(Calendar.DATE);
    calendar.setTimeInMillis(0);
    calendar.set(year, month, day, 23, 59, 59);
    return calendar.getTime();
    }

calendar.setTimeInMillis (0); zapewnia dokładność do milisekund

manik venkat
źródło
1
Te okropne klasy daty i czasu zostały lata temu wyparte przez nowoczesne klasy java.time zdefiniowane w JSR 310.
Basil Bourque
@BasilBourque pakiet java.time pojawił się tylko w Javie 8, który jest dostępny tylko od Androida N (API 26)
ivan8m8
@ ivan8m8 Większość funkcji java.time jest przenoszona z powrotem do Java 6 i 7 w bibliotece ThreeTen-Backport . Dalsze dostosowanie do wczesnego Androida (<26) w bibliotece ThreeTenABP .
Basil Bourque
@BasilBourque, ale ThreeTen używa wyjątkowo nieefektywnego mechanizmu na Androida .
ivan8m8
@ ivan8m8 Być może myślisz o poprzedniku java.time , Joda-Time . Zobacz ponownie projekt ThreeTenABP . Nie słyszałem o takiej nieefektywności na Androidzie przy użyciu tej biblioteki.
Basil Bourque
0

Wiem, że jest trochę późno, ale w przypadku Java 8, jeśli używasz OffsetDateTime (która oferuje wiele zalet, takich jak TimeZone, Nanoseconds itp.), Możesz użyć następującego kodu:

OffsetDateTime reallyEndOfDay = someDay.withHour(23).withMinute(59).withSecond(59).withNano(999999999);
// output: 2019-01-10T23:59:59.999999999Z
Florin
źródło
0

Miałem kilka niedogodności ze wszystkimi rozwiązaniami, ponieważ potrzebowałem typu zmiennej Instant i Strefy Czasowej zawsze ingerowałem w zmianę wszystkiego, a następnie łącząc rozwiązania stwierdziłem, że to dobra opcja.

        LocalDate today = LocalDate.now();
        Instant startDate = Instant.parse(today.toString()+"T00:00:00Z");
        Instant endDate = Instant.parse(today.toString()+"T23:59:59Z");

i mamy w rezultacie

        startDate = 2020-01-30T00:00:00Z
        endDate = 2020-01-30T23:59:59Z

Mam nadzieję, że Ci to pomoże

yOshi
źródło
Dzień faktycznie kończy się wraz z nadejściem pierwszej chwili następnego dnia. Twój kod przeskakuje przez ostatnią pełną sekundę dnia, miliard nanosekund, które nigdy nie są raportowane. Zobacz moją odpowiedź, aby dowiedzieć się o podejściu Half-Open do definiowania przedziału czasu.
Basil Bourque
Manipulowanie ciągami znaków jako sposobem obsługi wartości daty i godziny jest generalnie złym podejściem. Do tej pracy używaj inteligentnych obiektów zamiast głupich łańcuchów. W java.time zajęcia dają wszystkie funkcje potrzebne do tego problemu, bez uciekania się do manipulacji strun.
Basil Bourque
Właśnie dodałem sekcję tl; dr do mojej odpowiedzi, pokazującą, jak uzyskać zakres dnia jako parę Instantobiektów. Wskazówka: możesz być zainteresowany dodaniem biblioteki ThreeTen-Extra do swojego projektu, aby używać jej Intervalklasy.
Basil Bourque
0

Myślę, że najłatwiej byłoby coś takiego:

// Joda Time

DateTime dateTime=new DateTime(); 

StartOfDayMillis = dateTime.withMillis(System.currentTimeMillis()).withTimeAtStartOfDay().getMillis();
EndOfDayMillis = dateTime.withMillis(StartOfDayMillis).plusDays(1).minusSeconds(1).getMillis();

Te milisekundy można następnie przekształcić w kalendarz, natychmiastową lub lokalną datę zgodnie z wymaganiami za pomocą czasu Joda.

szczęśliwy wirus
źródło
-2
public static Date beginOfDay(Date date) {
    Calendar cal = Calendar.getInstance();
    cal.setTime(date);
    cal.set(Calendar.HOUR_OF_DAY, 0);
    cal.set(Calendar.MINUTE, 0);
    cal.set(Calendar.SECOND, 0);
    cal.set(Calendar.MILLISECOND, 0);

    return cal.getTime();
}

public static Date endOfDay(Date date) {
    Calendar cal = Calendar.getInstance();
    cal.setTime(date);
    cal.set(Calendar.HOUR_OF_DAY, 23);
    cal.set(Calendar.MINUTE, 59);
    cal.set(Calendar.SECOND, 59);
    cal.set(Calendar.MILLISECOND, 999);

    return cal.getTime();
}
Jack Jin
źródło