Вопрос:

В DST (Америка / Los_Angeles), если я добавлю один день, он добавляет только 23 часа вместо 24

java dst

59 просмотра

1 ответ

163 Репутация автора

Вот пример кода

public class DateFormatSampleCode {
    public static void main(String[] args) throws ParseException {
        DateFormat sdf = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssZ");
        Calendar cal = Calendar.getInstance();
        cal.setTimeZone(TimeZone.getTimeZone("America/Los_Angeles"));
        cal.setTime(sdf.parse("2016-03-12T02:00:00-0800"));
        sdf.setTimeZone(TimeZone.getTimeZone("America/Los_Angeles"));
        System.out.println(sdf.format(cal.getTime()));
        cal.add(Calendar.DATE, 1);
        System.out.println(sdf.format(cal.getTime()));  
    }
}

Здесь ответ

"2016-03-12T01: 00: 00-0800"

, но с моей точки зрения так и должно быть

2016-03-12T03: 00: 00-0700

».

Автор: Dushyant Sapra Источник Размещён: 02.02.2017 07:46

Ответы (1)


2 плюса

37867 Репутация автора

Как вы знаете, «В течение 2016 года летнее время (DST) действует с 13 марта 2016 года в 2 часа ночи (по местному времени) до 6 ноября 2016 года в 2 часа ночи по местному времени)» ( https: //www.nist .gov / pml / деление времени и частоты / популярные ссылки / переход на летнее время-dst ). Таким образом, если вы добавите 24 часа к 12 марта в 2 часа ночи, вы точно достигнете того времени, когда часы будут перемещены вперед с 2 до 3 часов ночи. Так что я не думаю, что это кристально ясно, какой результат ожидать. Я бы сразу ожидал либо 02:00:00-0800или 03:00:00-0700(последний - то, что вы ожидали).

Вы используете Calendarкласс pre-Java-8 . Если результат задокументирован точно, я пропустил его. В документе только сказано, что дополнение «основано на правилах календаря». Размышляя об этом, проблема в том, чего ожидать, если вы начнете с 2 до 3 часов 12 марта. До 2 вы получите то же время 13 марта, 24 часа спустя. После 3 тоже легко, вы получаете то же самое время, только через 23 часа из-за изменений. В периоды между 2 и 3, то же время не существует 13 марта, поэтому выбор должен быть сделан. Кажется, выбор был вычесть один час. Кроме того, они решили сделать это также в 2:00:00 утра, но не в 3:00:00, чтобы сделать правило действительным в течение полуоткрытого интервала в один час. По крайней мере, это соответствует. Мы, вероятно, не можем полностью избежать неожиданных результатов.

java.timeКлассы Java 8, такие как, например ZonedDateTime, лучше документированы и, следовательно, более надежны. ZonedDateTime.plusDays()Например, добавляет день / с к локальной дате и конвертирует обратно в ZonedDateTime. Если местная дата-время находится в промежутке (как здесь), он «будет скорректирован на длину промежутка» (здесь 1 час). Так что ваш результат будет 2016-03-13T03:00-07:00[America/Los_Angeles]именно таким, как вы ожидали.

Один из возможных уроков: используйте java.timeклассы, если вы можете использовать Java 8.

Автор: Ole V.V. Размещён: 02.02.2017 11:57
Вопросы из категории :
32x32