RFC 5545 и другие стандарты, такие как JSCalendar определяет продолжительность P1DT12H
как один номинальный день плюс 12 точных часов. . Обычно это 36 реальных («точных» или «точных») часов, но:
- Если весенний переход на летнее время происходит в течение «одного номинального дня» этой продолжительности, то точная продолжительность будет только 35 часов.
- Если осенний переход на летнее время происходит в течение «одного номинального дня», то точная продолжительность составит 37 часов.
Но что, если начальная дата / время - ровно за один номинальный день до прерывистого периода? Например, продолжительность P1DT12H
добавлена к 2020-03-07T02:30
в America/Los_Angeles
, где летнее время начинается в 2020-03-08T02:00
. В таком случае, каким должно быть местное время в конце этого периода?
Это 2020-03-08T14:30
? 2020-03-08T13:30
? 2020-03-08T15:30
? Что-то другое? Также: почему?
Проблема в том, что наивный способ вычисления точной продолжительности заключался бы в том, чтобы добавить часть продолжительности даты с использованием номинальных единиц, затем преобразовать этот промежуточный результат в UTC и добавить временную часть продолжительности с использованием точного времени. Но этот промежуточный результат является недопустимым номинальным временем, которое пропущено, тогда местное время этого промежуточного значения будет 2020-03-08T03:30
(3:30, а не 2:30 AM), потому что RFC 5545 говорит:
Если описанное местное время не наступает (при переходе со стандартного на летнее время), значение ДАТА-ВРЕМЯ интерпретируется с использованием смещения UTC перед разрывом в местном времени.
Таким образом, используя эту интерпретацию спецификации, окончательный результат после добавления 12-часового точного времени должен быть 2020-03-08T15:30
или 15:30.
Это «правильный» ответ согласно RFC 5455? Если нет, то каким должен быть ответ и почему?
Или это двусмысленность стандарта и нет объективно правильного ответа?
1 ответ
Я надеялся, что кто-нибудь ответит. Вот мое понимание:
Здесь две концепции:
- Либо у одного есть DTEND, и он вычисляет ДЛИТЕЛЬНОСТЬ, которая, как вы установили, будет варьироваться, если во время мероприятия произойдет переход на летнее время, ИЛИ
- у одного есть продолжительность и он вычисляет DTEND. Лучше сделать это в UTC в целях безопасности.
Повторите свой вопрос: Но что, если начальная дата / время - ровно за один номинальный день до прерывистого периода? В таком случае, каким должно быть местное время в конце этого периода?
Для расчета DTEND номинальный день в одно и то же время переводит нас в неверное время. Если использовать UTC для расчета этого номинального дня, получится 3.30 ночи. В спецификации говорится:
В случае разрывов в шкале времени, таких как переход от стандартного времени к летнему времени и обратно, вычисление точной продолжительности требует вычитания или добавления изменения продолжительности скачка.
Я понимаю, что это означает «да», при вычислении РАСЧЕТНОЙ длительности (т.е. когда у вас есть DTSTART и DTEND) будет варьироваться в зависимости от точки событий в календаре, как вы отметили.
Повторите свой вопрос Но этот промежуточный результат является недопустимым номинальным временем, которое пропущено, тогда местное время этого промежуточного значения - 2020-03-08T03: 30 (3:30, а не 2:30 ... "
Да, однако при дальнейших расчетах, я думаю, вы ошиблись, добавив 12H к местному времени. Спецификация говорит, что используйте более раннее смещение UTC, которое я понимаю, чтобы использовать его для получения времени UTC, использовать UTC для вычислений, а затем конвертировать обратно.
Если описанное местное время не наступает (при переходе со стандартного на летнее время), значение ДАТА-ВРЕМЯ интерпретируется с использованием смещения UTC перед разрывом в местном времени.
Обратите внимание, что это смещение по Гринвичу . Таким образом, один номинальный день приводит нас к 2.30 утра, чего «не существует» в Лос-Анджелесе 8 марта, поэтому мы используем смещение по всемирному координированному времени перед временным интервалом. -8 часов, что дает нам UTC = 10:30
Плюс 12H дает нам 22:30 по всемирному координированному времени.
Если мы оставим для расчетов смещение -8, мы получим 14:30 по местному времени.
* Это не на 100% прописано в спецификации. Было бы хорошо, если бы для подтверждения было больше отработанных примеров.
Совет, который я видел в другом месте, заключается в том, чтобы сохранять время во времени UTC, выполнять вычисления во времени UTC, а затем для отображения рассчитывать местное время. *
RE: Это 2020-03-08T14: 30? Это «правильный» ответ согласно RFC 5455? Если нет, то каким должен быть ответ и почему?
Я так понимаю, 14:30. Я перекрестно проверял с помощью PHP, с расчетами в LosAngeles и во времени UTC перед DST и во время DST, используя оба datetime-> add https://www.php.net/manual/en/datetime.add.php и https://www.php.net/manual/en/datetime.modify.php и постоянно получал этот ответ.
Я думаю, что правильным является 2020-03-08T14: 30, потому что, если использовать смещение UTC, как указано, и рассчитывать в UTC, это то, что вы получаете.
Работа PHP
add a nominal day P01D
Before DST:
2020-03-06T02:30:00-08:00
2020-03-07T02:30:00-08:00 with modify
2020-03-07T02:30:00-08:00 add date interval
Over DST:
2020-03-07T02:30:00-08:00
2020-03-08T03:30:00-07:00 with modify
2020-03-08T03:30:00-07:00 add date interval
add a nominal day plus 12 H ie: P01DT12H
Before DST:
2020-03-06T02:30:00-08:00
2020-03-07T14:30:00-08:00 add date interval
Over DST:
2020-03-07T02:30:00-08:00
2020-03-08T14:30:00-07:00 with modify
2020-03-08T14:30:00-07:00 add date interval
Для проверки смещения: https: // www. timeanddate.com/worldclock/meetingtime.html?day=8&month=3&year=2020&p1=137&iv=0
Похожие вопросы
Новые вопросы
icalendar
iCalendar - это широко используемый формат данных для представления и обмена календарной и календарной информацией независимо от какой-либо конкретной службы календаря или протокола.