Обновлено для исправления:
В большинстве случаев да, то же самое, см. следующий пример для Бразилии при переключении с зимнего на летнее время:
ZonedDateTime zdt =
ZonedDateTime.of(2015, 10, 18, 0, 30, 0, 0,
ZoneId.of("America/Sao_Paulo")); // switch to summer time
ZonedDateTime zdt1 = zdt.truncatedTo(ChronoUnit.DAYS);
ZonedDateTime zdt2 = zdt.toLocalDate().atStartOfDay(zdt.getZone());
System.out.println(zdt); // 2015-10-18T01:30-02:00[America/Sao_Paulo]
System.out.println(zdt1); // 2015-10-18T01:00-02:00[America/Sao_Paulo]
System.out.println(zdt2); // 2015-10-18T01:00-02:00[America/Sao_Paulo]
Усечение происходит на местный график. Если вы выберете DAYS, тогда вы выбираете полночь. Согласно javadoc , truncate()
-метод, наконец, обращается к новому ZonedDateTime
и сдвигает время вперед на размер зазора (1 час).
Преобразование zdt сперва до LocalDate
(отключение временной части), а затем поиск его ZonedDateTime
-пары в заданном часовом поясе фактически одинаково для этой ситуации.
Однако для обратного случая возврата от летнего времени до зимнего времени есть одно исключение (спасибо очень большое спасибо @Austin, который дал встречный пример). Проблема заключается в перекрытии, когда нужно решить, какое смещение использовать. Обычно класс ZonedDateTime
спроектирован / задан для использования предыдущего смещения, см. Также этот отрывок из Javadoc :
Для Overlaps общая стратегия заключается в том, что если локальная дата-время попадает в середину перекрытия, тогда предыдущее смещение будет сохранено. Если предыдущее смещение не было, или предыдущее смещение недействительно, используется более раннее смещение, обычно «летнее» время.
blockquote>Если класс
ZonedDateTime
, следовательно, будет следовать своей собственной спецификации то обе процедуры все равно будут эквивалентными значениям:zdt.truncatedTo(ChronoUnit.DAYS);
должен быть эквивалентен
zdt.toLocalDate().atStartOfDay().atZone(zdt.getZone()).withEarlierOffsetAtOverlap();
Но реальное поведение в соответствии с примером @Austin и подтверждено мной в собственном тестирование:
zdt.toLocalDate().atStartOfDay().atZone(zdt.getZone()).withLaterOffsetAtOverlap();
Похоже на скрытую несогласованность в классе
ZonedDateTime
, мягко говоря. Если вы спросите меня, какой метод будет предпочтительнее, я предпочел бы защищать второй метод, хотя он намного длиннее и требует больше нажатий клавиш. Но у него есть большое преимущество, чтобы быть более прозрачным в отношении того, что он делает. Еще одна причина предпочесть второй подход:Он действительно получает ПЕРВЫЙ момент, когда местное время равно началу дня. В противном случае при использовании первого метода вам необходимо написать:
zdt.truncatedTo(ChronoUnit.DAYS).withEarlierOffsetAtOverlap();
В итоге я использовал Artistic Style , который обеспечивает форматирование Whitesmith с опцией «style = whitesmith».