Pull to refresh

Comments 77

В результате этого в стране теперь работает множество высоковольтных систем передачи прямого электротока

Качество перевода конечно огонь. Даже переводчик Гугла уже таких ошибок не делает.

на западе, где первые генераторы были куплены у немецкой AEG и установлены в Токио, частота в сети равна 50 Гц; на востоке, в Осаке, были установлены генераторы G.E., и используются 60 Гц.

Не знал, что Осака теперь находится к востоку от Токио :)

2016-12-31T23:59:60 is 1483228800
2017-01-01T00:00:00 is 1483228800 //здесь дублирующаяся метка времени

Что-то я не понял. Я не очень хорошо знаю си, но судя по исходнику https://www.netmeister.org/blog/epoch-time.c автор статьи преобразует строку "2016-12-31T23:59:60" в структуру tm а затем из структуры tm формирует unix timestamp. А чего он ожидал вообще? 2016-12-31T23:59:60 - такого времени не бывает. Автор сам подставил в аргумент функции mktime() дичь а потом жалуется на дублирующую метку времени. По хорошему, функция mktime() вообще должна отказываться работать когда в её аргумент подставляют невалидное значение.

Сама по себе корректировка времени - это костыль в несовершенных правилах счёта времени. Т.е. правила которые придумали люди для счёта времени расходятся с физическими явлениями (скоростью вращения Земли). Проблема не в unix-времени а в том, что сами правила счёта времени несовершенны.

такого времени не бывает.

Как раз бывает. Автор же там пишет про секунды коррекции, когда чтобы не сбить календарь нужно добавить в сутки дополнительную секунду. "Проблема" в том, что Unix писали не астрономы, и не учитывали такие вещи. Проблема в кавычках, потому что для обычных людей это не важно, а если тебе нужно хранить какие-нибудь астрономические данные, чувствительные к таким вещам, то просто не используй дефолтное Unix-время. Так что это просто любопытная техническая особенность.

Проблема" в том, что Unix писали не астрономы, и не учитывали такие вещи

Не считаю нужным учитывать все прихоти астрономов. Сегодня у них +1 секунда в году, а завтра они число секунд дробное придумают. Это всёравно что играть в шахматы с игроком, который находу придумывает свои правила.

Операционная система нужна чтобы решать конкретные практические задачи и она их решает. А то что кто-то захотел прибавить или убавить секунду в году - меня это не волнует, и я прекрасно понимаю разработчиков ОС которые за 50 лет так и не стали учитывать эту секунду.

Статья звучит как камень в разработчиков ОС, автор критикует метод расчёта unix timestamp, но не предлагает решения этой проблемы.

Из-за секунды коррекции получается неправильное число секунд между двумя датами, а это может быть важно не только астрономам.

Операционная система нужна чтобы решать конкретные практические задачи и она их решает.

я прекрасно понимаю разработчиков ОС которые за 50 лет так и не стали учитывать эту секунду.

Машиночитаемым вариантом передачи метки момента времени является передача Epoch Timestamp в виде числа — либо секунд, либо миллисекунд, я очень часто видел такие форматы на практике. Если в такую "консервативную" систему (не учитывающую коррекционные секунды) передавать метки даты в вышеупомянутом формате откуда-нибудь извне (где коррекционные секунды учитываются), то одна и та же метка после трансляции в человеко-читаемое время будет отображать как минимум разное количество секунд или минут на разных машинах.
А если вспомнить про ещё один иногда применяющийся паттерн, когда Epoch Timestamp передают и распознают как "время начала дня", и, получая Timestamp, извлекают из него только год, месяц, и день, то при передаче "метки начала дня" в такую систему, она после отбрасывания всех компонентов времени вообще может начать показывать другую дату.
Вы всё ещё считаете, что такие системы "решают конкретные практические задачи", и делают это правильно?

Формат unix timestamp во многих местах очень удобен. Например, чтобы обозначить время +1 сутки достаточно к текущему времени прибавить 86400. И для сравнения/вычисления дат не нужны никакие объекты типа DateTime.

Так а что если как раз не хватит той одной секунды, чтобы попасть в следующий день?

+1 сутки достаточно к текущему времени прибавить 86400

А потом приходит его величество летнее/зимнее время, и без всяких секунд ломает эту логику на проде 2 раза в год, т.к. день, неожиданно, длится 82800 или 90000. Это самая тупая ошибка, с которой сталкиваются при работа с датой/временем, и встречается она повсеместно.

Но если в UTC работаешь, то это ж не проблема.

Вот работаешь ты в UTC, а на другой стороне нужен отчет за сутки. Причем о каком-то там UTC они в жизни не слышали, им надо данные строго с 00:00 по 23:59:59 по текущей локали. И внезапно появляется проблема.

А видел еще баг на одном внутреннем портале одной большой госкомпании. Есть форма, в которой можно указать интервал дат для поиска, максимальный интервал 90 дней. И проверка интервала через никсовую отметку времени. Конечно же, все интервалы, проходящие через зимний перевод времени, позволяли сделать поиск только за 89 дней.

Они то внутри работают в UTC, вот только конечные клиенты почти всегда работают в локальной таймзоне, что и является постоянным источником проблем.

Ну это понятно. Я сам занят в сервисе, который работает по всему миру и пользователи используют неограниченный набор таймзон. Как раз тут и нужно прибить время к фиксированной таймзоне при хранении. Пользователь передаёт данные в своей таймзоне, если это интервал, то оба его конца конвертируются в timestamp независимо с использованием tzdata, и там будут учтены переводы времени.

При этом расчёты для внутренних целей можно делать простой арифметикой. Например, мне надо удалить неиспользуемые данные старше 7 дней. Я могу при этом использовать простую арифметику и вычесть 7*86400 из текущего количества секунд. Собственно иначе в какой таймзоне я должен считать?

Например, мне надо удалить неиспользуемые данные старше 7 дней. Я могу при этом использовать простую арифметику и вычесть 7*86400 из текущего количества секунд.

В итоге для одних данные останутся за 6.5 дней, а для других за 7.5 дней, потому что одни живут в +10:00, а другие в -7:00. Таймзона то фиксированная для хранения, но если таймзоны клиентов не учтены, то тоже могут быть проблемы. У даты/времени столько пограничных условий, что бахнуть может в любой момент.

В итоге для одних данные останутся за 6.5 дней, а для других за 7.5 дней

Так не будет. Пользователь загружал данные в своей таймзоне и наблюдает их изменение в ней же. Погрешность возможна только в районе часа при смене DST, а это не важно в данном случае.

Вот именно, он загружал в своей таймзоне, а удаляются они по UTC. При таймзоне UTC-6:00 будут удалены данные за 6 часов, по его локальному времени, а при таймзоне UTC+6:00 останутся данные за дополнительные 6 часов.

Нет, это не так работает. Допустим пользователь в Москве загружает файл в 15:00. В UTC это будет 12:00. Файл удалится через 86400 секунд, по UTC это будет 12:00 следующих суток. Для пользователя в его московской таймзоне это будет 15:00 следующих суток, плюс минус час, на случай перехода DST (которого в неудачно выбранной мной московской зоне нет).

Если это так или иначе связано с финансами (даже косвенно), то удалиться оно должно не через 86400 секунд, а через N дней, где день заканчивается в полночь по таймзоне города, указанного в договоре. Грубо говоря, в Петропавловске и в Калининграде день заканчивается в разное время.

Например, возьмем проверку своевременности подачи декларации о налогах. В Петропавловске-Камчатском крайний срок будет 1 апреля 12:00+00:00, а в Калининграде это будет 1 апреля 02:00+00:00. Разница всего 10 часов, а последствия могут измеряться от тысяч до миллионов штрафа.

Есть у нас и такие задачи. Пользователь говорит, что некое действие должно быть совершено в такое-то время в его таймзоне. При сохранении задачи время конвертируется в UTC и сохраняется. Дальше сервер делает выборки в зоне UTC, чтобы понять какие задачи надо выполнить. И хотя сервер работает в другой таймзоне, время выполнения будет то, что указал пользователь.

Вот, о чем я и говорил. Такое делать нельзя:

Я могу при этом использовать простую арифметику и вычесть 7*86400 из текущего количества секунд.

Так может вы обоснуете почему нельзя? Конкретная описанная мной задача не связана с пользовательскими таймзонами. Чиста бэкендная задача очистки. Какую таймзону нужно выбрать тогда?

Так вы сами же сказали, что запланированные действия уже оказались связанными с таймзоной пользователя, а не просто "вычесть 7*86400 из текущего количества секунд".

Если пользователь планирует событие, то он, конечно, планирует его в своей таймзоне, и она тут же конвертируется в UTC, сервер делает выборки тоже в UTC и ничего не знает о том, какая зона была у пользователя в момент создания задачи. Тут нет противоречия. Есть просто другой класс задач, где прямая арифметика с секундами является приемлемой, потому что никакой конкретной таймзоны для них нет.

она тут же конвертируется в UTC

И в конце очередного года после измерения вращения земли решают добавить високосную секунду. После чего это конвертированное значение становится неправильным на эту самую секунду.

Ну, об этом и статья, собственно.

При этом расчёты для внутренних целей можно делать простой арифметикой. Например, мне надо удалить неиспользуемые данные старше 7 дней.

Для внутренних целей вообще можно удалять данные старше примерно 8 дней, и отсчитывать их абсолютно любой арифметикой, не думая о секундах, поясах, летнем времени и т.д.

Проблемы возникают, когда цели не внутренние и Вам нужно точно считать. Вот тут и начинаются сложности.

Я сам занят в сервисе, который работает по всему миру и пользователи используют неограниченный набор таймзон. Как раз тут и нужно прибить время к фиксированной таймзоне при хранении.

Не всегда. Для внутренних расчётов, конечно, единая таймзона удобнее. Но, например, для отчётности по дням Вам уже нужно знать таймзону пользователя. Причём желательно ещё понять, отчёт нужен по дате в одной таймзоне или во всех локальных - например, 28 ноября 00:00 - 23:59 в New York и San Francisco пересекаются но не совпадают, но иногда нужно считать именно так.

И как третий вариант, время иногда нужно хранить вообще отдельно от таймзоны - пользователь синя в NY описывает собятие 28 ноября в 23:25, но место события вводится в другое поле и он его ещё не ввёл. Причём возможно Вам не понадобится перевести в UTC, но критично важны 23:35.

Бывает еще хуже.
Отчет надо клиенту на мобильном устройстве.
Вот только клиент в Москве, в отпуске или в командировке а вся серверная инфраструктура — во Владивостоке и при разработке решили что это ж не проблема — у нас клиенты из Владивостока и окрестностей....

Чаще всего причиной возврата другой даты становится то, что преобразование производятся в разных часовых поясах. Иногда к этому примешивается то, что в одной из взаимодействующих систем забыли обновить таблицы временных зон, в этом случае ошибка возникает даже для двух систем, настроенных на вывод времени в одной временной зоне.

А если вспомнить про ещё один иногда применяющийся паттерн, когда Epoch Timestamp передают и распознают как "время начала дня",

Бить по рукам. Потому что оно создает проблемы даже без лишних секунд - а просто из за разных и/или ошибочных таймзон и их баз. Если тебе нужна именно дата - передавай дату.

оно создает проблемы даже без лишних секунд — а просто из за разных и/или ошибочных таймзон и их баз

Создаёт, но конкретно здесь речь не об этом. "Консервативность" ОС с точки зрения коррекционных секунд — это точно такая же причина расхождения, как разные часовые пояса, НО. В отличие от проблем, вызванных устаревшей tzdb, проблемы, вызываемые отсутствующей поддержкой коррекции секундами тестированием так просто не выявишь — про него надо "просто" знать, и тесты иметь специально заточенные именно на диапазоны коррекции.


Если тебе нужна именно дата — передавай дату.

Ну а что такое "передавать дату"?
Строкой? А зачем, тратить столько лишних байтов на пересылку, а потом ещё на разбор того, что пришло?
Числом Epoch Day? Ну да, это можно и нужно. Но здесь регулярно вылезают оЧЧень интересные подводные камни, как то, скажем, отсутствие нормальной поддержки Epoch Day Stamp в вашем фреймворке работы с датами, тогда как поддержка epoch timestamp там есть практически везде. Сходу, насколько мне известно, даже гиганты типа Google часто не поддерживают такой формат пересылки в своих API — вы вот их как собираетесь по рукам бить?

Вот прямо строкой передавать да и хранить, да. Особенно между системами. Или в типе, который именно три числа хранит (год, месяц, день) без всяких "храним timestamp под капотом, а день вычисляем". Меньше вероятность того, что по дороге или обмене между системами где-то что-то странно конвертируется. Когда промежуточная система с датой ничего не делает, а только дальше передать должна. Все эти преобразования в тип даты и обратно внутри нее - как раз бесполезная трата байтов и разбор.

Если надо с этим делать арифметику - прообразовывать в тип времени, с которым действия производить можно, как можно ближе к тому месту, где арифметика происходит.

Вот прямо строкой передавать да и хранить, да.

Нет, хранить строкой плохо по сразу нескольким соображениям.
Во-первых, даты полагается не только хранить, но и делать над ними операции. Да вот хотя бы две недели к ней добавить, чтобы дату следующего события узнать. Для того, чтобы сделать операцию над сохранённой в строке датой, её нужно сначала разобрать, и делать это нужно будет всякий раз, когда делаешь с ней что-то помимо пересылки. Вытягивать её из удалённого хранилища чтобы такое проделать весьма дорого.
Во-вторых, хранение строкой подразумевает хранение даты в некотором формате, но отображение даты пользователю с учётом его настроек неизбежно требует конвертирование формата, а для этого дату опять нужно разобрать, а потом собрать обратно уже с нужным форматом.


Или в типе, который именно три числа хранит (год, месяц, день) без всяких "храним timestamp под капотом, а день вычисляем".

Такой тип с тремя числами хорош для операций (например для прибавления месяца поменять нужно максимум два числа, и правило смены там элементарное) — но они сравнительно редко поддерживаются в системах хранения, и, что вдвойне обидно, чем новее система, тем меньше шансы такую поддержку в ней иметь. Денормализовать одну дату в три отдельных поля — выход только отчасти, потому что с денормализованными данными работать не так удобно, и в остатке некий тип даты всё равно потребуется хотя бы чтобы его из функции нормально вернуть после операции. Потому я и считаю, что на самом деле next best thing при отсутствии нормально обрисованного типа-даты в системе — это дату хранить как Epoch Day, там хотя бы большой класс операций над датами делается в функциях без вывертов, и глаз потом меньше дёргается.


Но это всё цветочки, на главный мой вопрос вы не ответили: как вы собираетесь бить по рукам Google сотоварищи, у которых зачастую нет понятия "date" в их сервисах — там есть только "timestamp" (хоть и не всегда unix-овый).

Во-первых, даты полагается не только хранить, но и делать над ними операции. Да вот хотя бы две недели к ней добавить, чтобы дату следующего события узнать.

Проблема в том, что операции делаются гораздо реже, чем она между полудюжиной микросервисов (ну и начиная с браузера местами) передается, не обрабатываясь, по принципу "передай дальше". Если в каждом таком сообщении дату объявить предусмотренным языком/библиотекой типом 'дата' - то оно на каждом стыке парсится из сетевого формата и обратно будет. С вероятностью что что-то пойдет не так из-за особенностей библиотек и кривых настроек таймзон.

Поэтому пересраховываемся и передаем стокой везде где только можно. А вычисления - парсим эту строку и проводим вычисления по необходимости.

Тут за чем следить надо - чтобы парсилось, вычислялось и обатно в строку приводилось в одной системе, а не в каких-то соседних.

Нет, если у нас какое-нибудь поле в базе данных, по которому массово проводится фильтрация (прямо в базе) "найти записи за 3 дня назад" - тогда пользуемся типом базы данных. А если эта фильтрация на уровне приложения происходит - все равно будет преобразовываться формат записи базы в формат записи языка. Поэтому строка лежит в базе или нет - не очень существенно.

Гуглояндексов, разумеется, бить по рукам не получится, но интерфесов с их библиотек -- вроде бы немного меньше, чем собственных интерфейсов. Поэтому учитываем и переводим в строку как только соответствующая дата в наших сообщениях появляться начинает.

Проблема в том, что операции делаются гораздо реже, чем она между полудюжиной микросервисов (ну и начиная с браузера местами) передается, не обрабатываясь, по принципу "передай дальше".

Я в очередной раз напомню, всё-таки, что строка — это не единственная форма передачи даты, и альтернативой может стать передача числа дней от начала некой эпохи. Точно так же, как при передаче даты строкой нужно будет договориться о формате, при передаче даты числом нужно будет договориться о положении начала эпохи. Все остальные плюсы и минусы ровно как для строк, включая ширину поддержки диалекта (можно ещё дни добавлять и вычитать, конечно, но лучше всё-таки этого не делать), а киллер-фича состоит в экономии нескольких байтов на каждой пересылке. Дальше, как водится, идёт вкусовщина. Кому-то нравится возможность человеку прочитать, что за дата "ушла", кому-то это неважно.


Iv38
Ну да, меняться могут все три числа, про обрезание месяца-то я и забыл.
Обычно, кстати, при добавлении именно месяцев идут назад — потому что "месяц" не тождественен "30 дням", хотя "год" обычно тождественен "12 месяцев".
Из этого, также, следует, что если месяц прибавить, а потом вычесть, то совершенно необязательно получится дата, с которой вся цепочка начиналась, и поэтому хорошим стилем будет промежуточные операции делать на "чистых" интервалах, без привлечения дат.

Такой тип с тремя числами хорош для операций (например для прибавления месяца поменять нужно максимум два числа, и правило смены там элементарное)

Не обязательно два и необязательно элементарное. Если к 31.01 прибавить 1 месяц, то это какое число будет? Точно не 31.02. А как тогда правильно, округлиться до последнего числа февраля или валить в март? В любом из этих случаев надо ещё и знать високосный ли год.

Не считаю нужным учитывать все прихоти астрономов. Сегодня у них +1 секунда в году, а завтра они число секунд дробное придумают. 

Ну да, когда-то у них было 365 в каждом году, а у некоторых до сих пор 354. Это очень удобно для их практических задач определения фаз луны, да и разница времени между месяцами очень просто рассчитывается. А что времена года уезжают - это уже другая задача :)

То есть у нас есть два подхода:

  1. Хранить год/месяц/день…/мс, точно и удобно отображать, но нетривиально рассчитать разницу между двумя моментами и нужна сложная структура данных (усложняются часы).

  2. Хранить секунды или миллисекунды от заданного момента. Очень просто хранить и считать компьютеру, но нетривиально отображать.

А что времена года уезжают - это уже другая задача

А разве в масштабах периода жизни приложения/человека - это проблема?
Даже если взять 80 лет как продолжительность жизни, за них времена года сместятся меньше чем на месяц
Максимум, чем это может грозить - устареванием литературы, условно рекомендация устраивать посевную в апреле перестанет быть актуальной
Так ли это критично?

Часовые пояса такая же прихоть астрономов. Давайте на них тогда забьем? Ну начнет солнце вставать в 20:37, подумаешь, что такого

Вообще говоря время 2016-12-31T23:59:60 Бывает

Сама по себе корректировка времени - это костыль в несовершенных правилах счёта времени. Т.е. правила которые придумали люди для счёта времени расходятся с физическими явлениями (скоростью вращения Земли)

А какие можно придумать правила, если скорость вращения Земли непостоянна и в общем случае непредсказуема?

Не правила несовершенны, а скорость вращения Земли несовершенна. То быстрее крутится, то медленнее. Да ещё и количество оборотов вокруг собственной оси за один оборот вокруг солнца нецелое.

на западе, ... в Токио ... ; на востоке, в Осаке

так вот Токио восточнее Осаки

Просто оставлю здесь классическую байку про ракетные движки, железную дорогу и лошадиную задницу :) https://romx.livejournal.com/166141.html

Очень уж история происхождения unix эпохи напомнила

А почему проблема именно для UNIX? В других системах есть корректировка на секунды в соответствии с расчетами службы времени?
В изначальной статье мягкое с теплым смешали, а тут еще корявый перевод добавился.

В других системах время изначально 64 битное. И не в секундах, и в не наносекундах, а в 100-наносекундных интервалах. И не с 1900/1970/1971/2001 а с 1600 года. И в прошлое разумный отступ, и интервал способен учитывать размерности менее секунд, и в будущее огромный запас. И это все работает сразу, с самого первого релиза.

ну, теперь-то легко не повторять ошибок прошлого :)

"Ошибку прошлого" совершили в 1970, повторили в 1986-1996 (GNU, Linux, и т.д.)

А "не совершили" в 1988-1993, используя как основу систему из второй половины 1970х (к сожалению не знаю, как там время устроено).

Как мы видим, временые периоды почти одинаковы.

ну, самая большая лигаси ИМХО - это попытка постоянно представлять время в виде одного числа одной и той же размерности.

Гораздо лучше ему бы было в виде массива байт: чтобы биты первого байта задавали длину остальных (см. например как UNICODE), а остальные уже хранили число (наносекунд, секунд или 1/100 наносекунд и т.д.)

Такое допустимо для передачи значений, но любая обработка такого значения превратится в ад с массой проверкой и кучей особых случаев. Обрабатывать гораздо проще значения с фиксированным форматом.

Мне вот непонятно, разве нельзя предсказать на годы вперед где окажется земля в тот или иной момент времени? Можно же было бы тогда расчитать все восходы и закаты на годы вперед. Тогда не пришлось бы делать коррекцию постфактум, а просто перещелкивать дни по табличным значениям. Или тут есть какая то доля непредсказуемости из-за влияния других планет?

Ну это понятно, просто на каком отрезке времени доля хаоса становится больше секунды, миллисекунды? Ну то есть к примеру если на отрезок лет 50 можно рассчитать, даже с учётом хаоса, то потом можно посчитать по новой, лет чрез 50, 20, 10.

если вам для "ну будет минутой больше или меньше - и так сойдет", то можно наверно и на 100 лет вперед рассчитать

Для такого необходимо знать все гравитационные силы воздействующие на тело, а учитывая, что огромная часть массы скрыта пересчет думается происходит постфактум, когда предсказанная и фактическая разница измерений случается.

UFO just landed and posted this here

1) а как вы думаете - с какой точностью делают измерения положения и скорости Земли на орбите? А также положения и скорости других небесных тел, влияющих на Землю ? (полмиллиметра на миллион тонн массы или меньше? или больше ?)

2) какие у вас критерии - что влияет на траекторию Земли, а что - не влияет ? (пояс астероидов и Меркурий - влияют ? или только Луна и Солнце ?)

3) и, как вы думаете - как быстро накапливается расхождение фактического положения от предрассчитанного со временем ? (на микроградусы в год или больше ? или меньше ?)

не знаю, потому и спрашиваю.

ну просто если "рассветы и закаты - для людей", то там рассчитывают очень примерно (ибо еще и высота над горизонтом у всех будет разная), и там можно надолго вперед рассчитать.

А если вы - астроном и вам нужно прицелиться на нужную звезду с поверхности Земли, то там увы одна секунда ухода в несколько лет - это именно то, что "не могут рассчитать заранее" (а иначе - просто рассчитывали бы и в ус не дули)

> а как вы думаете - с какой точностью делают измерения положения и скорости Земли на орбите

если Вас интересует годичный параллакс, то он незначителен max порядка долей угловой секунды, т.е в большинстве приложений можно считать что звезды на бесконечности, в первом приближении имеет значение только вращение земли

> А если вы - астроном и вам нужно прицелиться на нужную звезду с поверхности Земли

чтобы точно прицелиться на нужную звезду зная ее угловые координаты желательно иметь стабильную монтировку, и соответствующие средства управления (включая привода, угловые датчики, контроль механических деформаций и пр. ) в общем случае точность такого прицеливания на 2-3 порядка хуже точности знания координат звезд по каталогу, что тем не менее достаточно для попадания в поле зрения, но для точного наведения обычно используется относительный метод с распознаванием звездного узора

Сначала нужно составить объёмную точную гравиметрическую карту Земли - распределения масс в объёме; а потом повторить этот фокус для Луны и Солнца.

Для горизонта лет в пару хватит, а там можно и окружение притягивать.

Только, пока гравиметрия Земли оперирует блоками в сотни и тысячи километров, отсутствует какая либо адекватная модель происходящего внутри планеты (ядро плюс мантия), и да, прогнозы строятся и до недавнего времени они даже примерно попадали. :)

Примерно рассчитывали на десятилетия вперёд еще до нашей эры. Даже делали механические компьютеры для рассчета фаз Луны, затмений, положения планет на небе и т.п.

По мне всё проще: Лень и Зачем?!

Зачем на годы вперёд всё подсчитывать? Если вы знаете (например), что коррекция будет через 173 года ... то что?

Ок, слишком далеко. Пусть коррекция будет через 2 года ... и ... что? Броситесь переписывать использование функций времени с учётом коррекции? Добавлять/убавлять? А если функции уже будут с учётом коррекции (ОЧЕНЬ вероятное событие)?

Если в одном календаре (например, григорианский) коррекция есть, а в другом (юлианский, иранский, еврейский, ...) коррекции нет, ... то ... что?

Скорость вращения Земли (и коррекционные секунды) — нет (пока) нельзя.

Может не надо дёргать время UNIX вслед за астрономическим? Пусть идёт себе равномерно. А для конвертаций в воспринимаемый человеком вид, использовать журнал с количеством секунд в каждом году.

Надо как-то этот журнал по всем системам рассовывать постфактум.

в эпоху повсеместного распространения интернета и операционок которые обновляются не спрося у пользователя разрешения это не большая проблема. но в целом я согласен что идея фиговая и очень костыльная. да и реализация породит 100500 несовместимых форматов этого журнала и кучу конвертеров с багами и артефактами.

ну вот таймзоны - уже и так распихиваются.

И сколько было с ними "особенностей"?
И то что на андроиде tzdata обновлялось с обновлениями Андроида, ведь разумеется всякие изменения таймзон всяко больше чем за года принимают (см например https://habr.com/ru/post/130305/ ) да и сами обновления производители для всех устройств устройств выпускают сразу как гугл выпустит для Nexus/Pixel.
И то что с самого начала (а не с 2011) tzdata поддерживалась авторитетной международной организаций (см например habr.com/ru/post/130587/ )

Вот сейчас переименовалась киевская таймзона. Сколько с этим проблем. От пользователей она уже приходит, а сервера о ней знать не знают. Надо всё обновлять. Либо городить костыли с подменой таймзоны и огрести из-за этого проблем чуть позже, когда tzdata таки обновится.

Вот кстати не очень понятно — почему вообще в таких случаях (определение зоны НЕ меняется — меняется только название, с Киевом это ж не уникальный случай, была еще как минимум Asia/Calcutta которая стала Asia/Kolkata) не введено жесткое правило что вносится новый алиас, а старое название не выкидывается вообще никогда (или выкидываеться но лет через 10 минимум?), при этом новое название становится основным и отправляется автоматически/возвращается из системных API не менее чем (допустим) через 3 года (из тех соображений что если где то за 3 года tzdata не обновилась — значит уже и не обновится).
Именно как жесткое правило

Не очень понял как это должно работать. Вот допустим переименовали зону europe/zona в europe/zone. Пользователь, например, винды получил обновления зон с очередным апдейтом, теперь там есть обе зоны, они идентичны. Пользователь хочет поменять в настройках винды зону europe/zona на europe/zone. Он может это сделать? Если да, то потом его браузер отправит эту зону какому-нибудь ничего не подозревающему серверу, где tzdata не обновлена. Или надо добавить зоны, но запретить их использовать первые три года? Кажется, что это почти невозможно обеспечить. И добавление новых зон не алиасов всё равно будет вызывать проблемы.


Может лучше брать актуальные данные из какой-то внешней стандартизированной базы через сеть, если есть такая возможность? Что-то вроде DNS но для таймзон. Не нашёл в кэше, спроси вышестоящий сервер.

Имелось ввиду:


  • если пользователь хочет поменять — ну пусть меняет, не все ж поменяют, а если будут проблемы в работе какой то программы/сервера — это уже либо проблемы пользователя либо пользователю надо убеждать авторов оной программы что надо фиксить срочно (вот судя по гуглежу — украинцы много где продвигали эту замену с Киевом, находится куча багов) но как быть если обновить ну нельзя?(в старых версиях андроида обновление было только с новой версией).
  • без прямой команды пользователя — использовать старую зону
  • если старой зоны в принципе не существует — тут выхода нет.

После ковыряния в вопросе кстати выяснилось что как минимум на самой базы то решение похоже есть — есть такая штука как ссылки — см например https://data.iana.org/time-zones/tzdb-2023a/backward — там и Kiev / Kyiev и другие интересные примеры вроде Стамбула который и Asia/Stambul и Europe/Stambul


Может лучше брать актуальные данные из какой-то внешней стандартизированной базы через сеть, если есть такая возможность?

Оно и так лежит на https://data.iana.org/time-zones — и исходники и скомпилированные версии. Проблема собственно в том что очень много где — обновление либо не предусмотрено без обновления конкретного ПО либо берется с системы а в системе оно не обновляется
(ну как пример(для случая с Киевом — не актуальный) — на андроиде — до 8.1 — обновление с обновлением прошивки, ну или рут и простенький апдейтер вроде https://github.com/meefik/tzupdater, 8.1-9 — можно не выпускать обновление прошивки но обновление должен, 10+ — гугл может обновить)

Вращение Земли ускоряется и замедляется непредсказуемо. Если вы хотите согласовывать значение аппаратных часов с астрономическим временем, то у вас нет другого варианта кроме как рассовывать журнал постфактум. Заранее узнать об изменении скорости вращения невозможно - часы придётся тем или иным способом "подводить". Кроме того, постоянно меняются часовые пояса и правила перехода с летнего времени на зимнее. Эту информацию тоже приходится как-то доводить до конечных систем. Так что решение не двигать UNIX-время очень разумное. Кстати, точно так же не двигается GPS-время и TAI-время.

время измерялось в 1/60 секунды, а не в секундах

Забавно здесь то, что эта частота прерываний зависит от частоты в сети источника питания.

А то я уж про терции подумал ?

Вот что происходит, когда люди начинают частности натягивать на "вообще".

Смотрим на POSIX: https://pubs.opengroup.org/onlinepubs/9699919799/functions/time.html

там сказано про секунды от "эпохи". Указание на 01.01.1970 есть? Нет! Т.е. условная линукса может считать от любой даты!!! Весело?

Смотрим на C++:

https://en.cppreference.com/w/c/chrono/time

формат представления не специфицирован (хотя обычно совпадает с POSIX) - т.е. это могут быть хоть 1/60 секунды, хоть минуты. Весело?

По факту возвращаемое время может быть в любых интервальных единицах от любой базовой даты.

Учите МатЧасть, читайте стандарт.

извините, а это не вы автор проигрывания музыки и показывания веселых картинок, когда программа на С++ натыкается на UB ?

Sign up to leave a comment.

Articles