Комментарии 42
А что, TZ у вас одна на все события, во всех последовательностях?

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

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

Совершенно не факт, что все это стоит добавлять, но посмотреть можно на любую библиотеку с поддержкой формата iCal например, и прикинуть, что они умеют. Да и импорт-экспорт iCal наверное не помешает.
TZ у вас одна на все события

TZ это атрибут инстанса DateTime, очевидно. Вот сниппет из продакшн-кода, отвечающий за стрим слотов, когда fx-markets закрыты, с корректной обработкой DST, между прочим:


    first_weekend = %Slot{
      from: DateTime.from_naive!(
          ~N|2018-01-05 21:00:00|,
          "America/New_York"),
      to: DateTime.from_naive!(
          ~N|2018-01-08 08:59:59|,
          "Australia/Sydney")
    }

    weekends =
      Stream.iterate(
        first_weekend,
        fn acc ->
          acc
          |> Tempus.Slot.shift(from: @μs_in_week, to: @μs_in_week)
          |> Tempus.Slot.shift_tz()
        end
      )

события и интервалы бывают повторяющимися

Вот выше пример, там повторяющиеся события. Stream же.


у того, что вы называете слотами, бывают свойства — произвольные

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


посмотреть можно на любую библиотеку с поддержкой формата iCal например, и прикинуть, что они умеют

Я решал практическую задачу, а не писал сферическую библиотеку в вакууме. Но, да, посмотрю, спасибо за наводку.


импорт-экспорт iCal наверное не помешает

Наверное, да, посмотрю тоже, спасибо.

Сферическую это не про iCal — просто это же в принципе обычный типовой календарь, а их часто рисуют где-то в аутлуке. Ну и и экспорт самый удобный в iCal, поэтому его поддержка это просто тупо удобно. Хотя сам формат — на мой взгляд типично дурацкий.

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

>Вот выше пример, там повторяющиеся события. Stream же.
Понял. Просто без знания синтаксиса это было не очевидно.

Что до TZ — то тут скорее вопрос в том, где вы берете их описание (и как обновляется их база). А уж если даты в прошлом (особенно далеко в прошлом) — то и подавно не очевидно, где брать описание зон.

Вообще, решить для произвольной даты, America/New_York и -5 — это одно и тоже, или же нет, не всегда тривиально. А уж если интервал захватывает какой-то переход на летнее время — то и подавно (потому что на концах интервала время может плавать на час туда-сюда, и по-идее, похожий на вид интервал в разных зонах может оказаться разной длины).
Если бы я мог не работать… :) к сожалению, у нас в некоторых базах бывают даже даты 1 января 0 года (до нашей эры к счастью не встречались). И проблем с ними, прямо скажем, дофига — потому что когда в процессе завязаны скажем БД Оракл (разных версий), MS SQL (тоже разные), Oracle Golden Gate (или OGG BDA). Java, Spark, Hive, Impala, и т.п., и добиться чтобы все это работало согласованно, да еще и с единой базой зон — это практически недостижимо.
где вы берете их описание (и как обновляется их база)

В Unicode Consortium’s Common Locale Data Repository, а где еще? Обновляется каждый день.


похожий на вид интервал в разных зонах может оказаться разной длины

Это на себя берет DateTime из поставки эликсира с правильным календарем (Cldr). Туда можно хоть еврейский календарь засунуть, и все будет работать.


если интервал захватывает какой-то переход на летнее время — то и подавно

dt = DateTime.from_naive!(~N|2020-11-01 00:00:00|, "America/New_York")
#⇒ #DateTime<2020-11-01 00:00:00-04:00 EDT America/New_York>
DateTime.add(dt, 3600, :second).hour
#⇒ 1
DateTime.add(dt, 7200, :second).hour
#⇒ 1

Внутри я добавляю микросекунды, так что тут все чисто.

>Внутри я добавляю микросекунды, так что тут все чисто.
Я про другое — интервал в одной зоне может в другой просто не существовать, потому что перевод на летнее/зимнее время иногда выглядит так: у нас было 0 часов вчера, а потом сразу бац — и час ночи сегодня. Все что между нулем и часом — в этой зоне не существует. При этом, насколько я понимаю, тут могут вылезать разные странные случаи при любой обработке такого кейса.

>Это на себя берет DateTime из поставки эликсира с правильным календарем (Cldr).
Тут не очень понятно, что значит «правильный», если в разных календарях 00:05 либо является валидным временем, а в другом календаре это же время не существует? Оба календаря по своему правильные — но друг с другом они конфликтуют.

Не факт что это существенно для любой системы, но у нас вот вылезает время от времени. Скорее всего, если вы планируете визит к стоматологу, вы на такое никогда не наступите. Но если стоматолог в другой зоне свой календарь ведет — то могут быть разные странности.
если в разных календарях 00:05 либо является валидным временем, а в другом календаре это же время не существует

Я не понимаю, где тут возможна проблема. Добавить слот с таким временем не позволит Slots.add/2. Slot.valid?/1 вернет false, потому что время не валидно.


Tempus.add/4, как я показал выше, отработает корректно. Никаких конфликтов календарей нет, они диффеоморфны. Функция преобразования одного в другой — задана реализацией календаря.


если стоматолог в другой зоне свой календарь ведет

Я выше же опубликовал пример вот ровно для этого случая. Fx-рынки открываются в понедельник в 9:00 в Сиднее и закрываются в 22:00 в пятницу в Нью-Йорке. По местному времени, да. DST в этих городах вообще не согласовано никак.



И мой код прекрасно с этим справляется; это была почти ключевая задача этой библиотеки (помимо просто планирования переговорок): стрим добавляет по 86400 секунд к понедельнику, 8 утра по Сиднею и пятнице, 10 вечера, по Нью-Йорку. А потом переводит получившиеся значения в UTC для дальнейших операций. Разница между from и to плавает в пределах двух часов, в зависимости от времени года.


Надо будет этот момент поподробнее разжевать в документации, а то мои коллеги тоже не поверили, что все так радужно :)

>Я не понимаю, где тут возможна проблема.
>Добавить слот с таким временем не позволит Slots.add/2. Slot.valid?/1 вернет false, потому что время не валидно.
Что значит не валидно, когда оно валидно (в другом календаре)? Ну смотрите, это по Москве, какого-то марта непонятного года, когда был переход на летнее время не было интервала времени с 0 до часу ночи. Но в другом календаре это время вполне валидно. Ну или в наших терминах, как у меня в проекте — Оракл DB считает, что эти вот 05 минут первого вполне правильное время (потому что у него оно например в UTC), а Java на нашей стороне — уже нет (потому что мы пытаемся преобразовать его в MSK, например), и корректирует его на 01:00.

Я не говорю что с этим ничего сделать нельзя, просто поведение в таком случае вполне может быть неожиданным с точки зрения юзера где-то в UI. Я даже не исключаю, что к вашей библиотеке это вообще отношения не имеет, но проблема такая есть, и вполне реальная.
Что значит не валидно, когда оно валидно (в другом календаре)?

Календарь — атрибут инстанса DateTime. Время без календаря называется NaiveDateTime и в принципе не имеет смысла в расчетах с вовлечением разных временны́х зон.


Java на нашей стороне — уже нет (потому что мы пытаемся преобразовать его в MSK, например)

Это шутка? Совершенно очевидно, что любое время в UTC можно конвертировать в любую другую таймзону, включая MSK. Это напрямую следует из непрерывности временной координаты пространства-времени. То, что ваш код не справляется с тем, чтобы сделать это правильно — не вина времени, Оракла, или Java.


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

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

>Это шутка? Совершенно очевидно, что любое время в UTC можно конвертировать в любую другую таймзону, включая MSK. Это напрямую следует из непрерывности временной координаты пространства-времени.
Нет, это совершенно не шутка. Нет никакой непрерывности. Переход на летнее время осуществляется как я написал ранее — после 0 часов следует сразу 1 час ночи. Скажем так — в некоторых системах это так работает. Если вы такого не видели — не значит что так не бывает.
Если вы такого не видели — не значит что так не бывает.

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


0:30 MSK в базе оказаться не может, если код писал не криворукий дебил. Время в UTC (и любой другой зоне), переведенное в MSK, внезапно оказаться 0:30 MSK не может. Такому времени неоткуда взяться.


Если кто-то хранит время без зоны, а потом цепляет к нему MSK и удивляется — этого человека имеет смысл уволить вчерашним днем.


Как я показал в примере выше, мой код с входными данными 23:30 MSK + minutes(31) в этот конкретный день — вернет 1:01 MSK. Если вы продолжаете считать, что там есть какие-то сложности — я предлагаю еще раз подумать, найти все места, где время хранится без таймзон, и переписать все правильно.


Еще раз, для закрепления:


dt = DateTime.from_naive!(~N|2020-11-01 00:00:00|, "America/New_York")
#⇒ #DateTime<2020-11-01 00:00:00-04:00 EDT America/New_York>
DateTime.add(dt, 3600, :second)     
#⇒ #DateTime<2020-11-01 01:00:00-04:00 EDT America/New_York>
DateTime.add(dt, 7200, :second)     
#⇒ #DateTime<2020-11-01 01:00:00-05:00 EST America/New_York>
>0:30 MSK в базе оказаться не может, если код писал не криворукий дебил. Время в UTC (и любой другой зоне), переведенное в MSK, внезапно оказаться 0:30 MSK не может. Такому времени неоткуда взяться.

Вы не поняли. Оно не оказывается 0:30. Оно преобразуется в ближайшее валидное. Именно это и является для пользователей неприятным сюрпризом.

Если честно, я и правда уже мало, что понимаю.


Для пользователя оказывается сюрпризом, что ему показывают правильное время вместо несуществующего?

> Условно 20:59 utc это 23:59 msk, 21:00 utc это 0:00 msk, а 21:01 utc это 01:01 msk.

Ну вот смотрите. alexzeed ниже привел пример, как это должно выглядеть с его точки зрения. Я согласен, что это выглядит логично. Но проблема в том, что в реальности это бывает не 01:01, а ближайшее валидное время, то есть скажем 01:00. И минуты при этом пропадают. И обратно в UTC это уже не сконвертировать без потерь.

Если кто-то хранит время без зоны, а потом цепляет к нему MSK и удивляется — этого человека имеет смысл уволить вчерашним днем.


Он все-таки видимо не совсем так делает, хотя близко к этому. Но главное эффект такой как я выше описал. А уволить при этом придется слишком многих, потому что у нас например, эта проблема всплывает во взаимодействии Oracle DB, Oracle Golden Gate, Java, Hive.
Но проблема в том, что в реальности это бывает не 01:01, а ближайшее валидное время, то есть скажем 01:00. И минуты при этом пропадают. И обратно в UTC это уже не сконвертировать без потерь.

Да вы издеваетесь, что ли?


Куда пропадают минуты? С какого, простите, хрена, они куда-то пропадают?


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


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


Ее нет, так же, как нет проблемы деления на ноль. На ноль не делят, а если делят, то получают фигню — и обвинять в этом ноль — по меньшей мере странно. И alexzeed все изложил предельно корректно и верно.

>Куда пропадают минуты? С какого, простите, хрена, они куда-то пропадают?

Объясняю на пальцах — если Java парсеру из строк в даты подсунуть вот такую невалидную дату (т.е. 00:05, с таймзоной, само собой) — то она преобразуется в ближайшую валидную. Всех деталей я уже не помню, но в целом поведение было именно такое. И я вас уверяю, оно документированное — т.е. это такая фича. Почему так? ХЗ, я могу только предположить. Ведь java дата — это по сути просто число миллисекунд от начала времен, и с переходом на летнее время в таком представлении всегда проблемы будут, потому что берете вы число миллисекунд в 00:00, прибавляете скажем 30 секунд — и получить вы должны не 00:30, а час ночи.

Ваша проблема связана с некомпетентностью разработчиков, работающих с временами в вашей этой связке.


Ну, с большой вероятностью это разработчики Golden Gate — потому что а) невалидная дата в виде строки приходит именно от них б) у них были и другие баги с временными зонами. И я бы охотно последовал вашему совету их уволить — но увы, ни одной вменяемой альтернативы OGG в природе не существует, поэтому с их багами приходится мириться.

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


https://repl.it/repls/IntelligentSpottedDowngrade


Ввод:


import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;

class Main {
  public static void main(String[] args) {
    try {
      String input = "Sun Mar 08 02:30:00 EDT 2020";
      SimpleDateFormat parser = new SimpleDateFormat("EEE MMM d HH:mm:ss zzz yyyy");
      Date date = parser.parse(input);
      String formattedDate = parser.format(date);

      System.out.println(formattedDate);
    } catch (ParseException pe) {
      System.out.println("Oooups");
    }
  }
}

Вывод:


$ javac -classpath .:/run_dir/junit-4.12.jar:target/dependency/* -d . Main.java
$ java -classpath .:/run_dir/junit-4.12.jar:target/dependency/* Main
//⇒ Sun Mar 8 01:30:00 EST 2020
А что, 8 марта 2020 в этой зоне переход на летнее время?

То что вы показываете — не единственный «стандартный» парсер, потому что у нас Java 8, и там есть и другие. И не единственный возможный режим парсинга. Ну и главное — у вас время на выходе уменьшается, т.е. из 02:30 получается 01:30, а это не наш случай. У нас переход в обратную сторону, когда 00:00 становится 01:00.

>Я не имел дел с ораклом и джавой уже почти 20 лет
А я с ними каждый день имею дело. И у меня примерно 100 или чуть больше разных ораклов, и штук 20 MS SQL. Я вполне понимаю ваше возмущение на тему «ну не может же там быть такой фигни», но уж поверьте — может. Вот прямо так сразу все детали не вспомню, но если любопытно — завтра постараюсь найти.
Ну и главное — у вас время на выходе уменьшается, т.е. из 02:30 получается 01:30, а это не наш случай.

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


Между двумя и тремя часами ночи в этот день в этой таймзоне происходит перевод стрелок вперед. Времени 2:30, таким образом, не существует. И никто никуда никого не округляет, но корректно переводит в зимнее время, потому что 3:00 еще не наступило. Когда наступит, перевод осуществится в летнее время. Корректно. Без округлений и смс.


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


alexzeed не понимаю, что вас удивляет в вашем же примере и зачем вы обзываете авторов джавы. Время никуда не округляется, время корректируется, причем корректируется правильно. Там нет никакого UB, представьте себе рулетку с выкушенным куском 10см-20см. Если вы станете отмерять 15см — увидите 25см, и это правильно. Разумно, и ожидаемо.


Вы запросили 03:30 EET, вам вернули 04:30 EEST. На зону обратите внимание тоже.

>Я опроверг ложный тезис
Какой еще тезис? Посмотрите ответ alexzeed ниже. Более того, о том, что оно округляется — это только вы и говорите, поэтому непонятно, чего тут нужно было опровергать?

Я такое слово «округляется» не употреблял, alexzeed тоже. Я говорил, что оно становится ближайшим валидным — то есть в моем случае часом. Приведенная ниже цитата из документации это полностью подтверждает.

Разница между вашим примером и нашим реальным видимо может состоять в том, что в реальном таймзона задана через setTimeZone у SimpleDateFormat, либо по-умолчанию (что в общем почти одно и тоже). Хотя как мы видим ниже, в таком варианте оно тоже проявляется.

И еще ваш пример отличается тем, что у вас две разные зоны для зимнего и летнего времени, EST и EDT. У нас же зона ровно одна, московская. Это как минимум другой случай.
проблема в том, что в реальности это бывает не 01:01, а ближайшее валидное время, то есть скажем 01:00. И минуты при этом пропадают. И обратно в UTC это уже не сконвертировать без потерь.

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

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


«Становится ближайшим валидным» и «округляет» — это одно и то же, вообще-то. Минуты, разумеется, никуда не пропадают. А приведенная цитата говорит о том, что время правильно сдвигается в правильную сторону.

Знаете, почему у вас карма -14, при том что вы достаточно умный? Потому что вы самоуверены до безобразия. Я не собирался вам ничего доказывать. Вы не работали ни с ораклом ни с Java 20 лет — но все еще уверены, что все о них знаете. Вы написали 1 тест — и решили, что все доказали. Ступайте мимо.
Знаете, почему у вас карма -14, при том что вы достаточно умный?

Конечно. Потому что я не стесняюсь указывать людям недостаточно умным на то, что они недостаточно умные. Я ценю отрицательную карму на этом ресурсе, она мне льстит.


Ступайте мимо.

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

Вовсе нет. Во-первых, я предпочитаю вариант «Разве нас может интересовать мнение человека лысого и вот с таким носом». А во-вторых, это просто мнение об авторе, без попытки что-либо доказать. Без хамства, причем. Он считает меня недостаточно умным, а я его. Ну и норм.

Это тоже аргумент к человеку.


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

Знаете, почему у вас карма -14, при том что вы достаточно умный?
Он считает меня недостаточно умным, а я его. Ну и норм.

Ловко вы прям на лету переобуваетесь. Ну ничего, на хабре это любят. И ад хоминем любят, если он против кого надо ад хоминем.

А мне тоже непонятна проблема с 0:30. Условно 20:59 utc это 23:59 msk, 21:00 utc это 0:00 msk, а 21:01 utc это 01:01 msk. И все. Не может быть 0:30 msk в этот день, неоткуда ему взяться, если кто-то при парсинге 0:30 мск вместо эксепшена превращает его молча в 01:00, то он нехороший редиска, но время тут ни причем.

Я вас уверяю, этот нехороший человек — это кто-то из авторов java рантайма. То есть, такое происходит, если вы парсите дату в нормальном формате, с зоной, совершенно стандартным механизмом. Конкретных деталей не приведу — во-первых, это было года полтора назад, а во-вторых, я тот тест не писал, а только читал. Но если интересно, могу в понедельник поискать, без гарантии успеха.
Приношу свои извинения, был самоуверен. Мнение, что авторы джава рантайма нехорошие редиски, не изменю :) И не только из-за этого момента с некорректным временем. Мой опыт разработки на джаве лет 7, но именно с парсингом локального времени не сталкивался. Да, оказывается при парсинге времени, которое попадает в дырку перехода на летнее прибавляется 1 час:
new SimpleDateFormat("dd.MM.yyyy HH:mm zzz").parse("29.03.2020 03:30 EET").toString()
дает "Sun Mar 29 04:30:00 EEST 2020". Для SimpleDateFormat в доке не нашел, а для ZonedDateTime этот ноговыстрел действительно задокументирован (класс ZonedDateTime: For Gaps, the general strategy is that if the local date-time falls in the middle of a Gap, then the resulting zoned date-time will have a local date-time shifted forwards by the length of the Gap, resulting in a date-time in the later offset, typically «summer» time). Остаюсь при мнении что тут должен эксепшен выскочить вместо хитрых коррекций.
Вообще, мне это напрминает обработку ситуаций Undefined Behavior в С++. Типа, «такого не должно быть, поэтому делаем что хотим».
Ну и такая штука не должна возникать при работе с базой. Она должна возникать на уровне ввода пользовательских данных, или с UI, или допустим из какого-то CSV файла, в общем — снаружи системы. А внутри все времена должны представляться в каком-то непрерывном формате, тогда таких приколов не будет.
>Приношу свои извинения, был самоуверен.
Да ладно, мы вполне культурно пообщались, без негатива. Тем более всем интересно, и пример вы в конечном счете самостоятельно раскопали. Вы с chapuza явно оба неленивые, любите докопаться до истины :)

Я ведь в общем и не спорил, что такое поведение — оно не совсем явное, и было бы неплохо либо выкинуть исключение, либо что-то еще сделать, чтобы было понятно, что такое вот произошло. Но факт что оно вполне описано, и тут уж не особо пожалуешься.

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

>Ну и такая штука не должна возникать при работе с базой.
Ну как-бы на стыке OGG и Hive — это примерно и есть снаружи. И на csv воспроизводилось. То есть, вы в csv кладете такую вот дату, говорите Hive, что этот файл есть таблица вот такой структуры — и опа, в таблице уже часы поменялись.

Опять же, не должна — это в идеальном мире :) В нашем реальном оракл позволяет хранить в базе невалидные даты. То есть польностью невалидные, отрицательные компоненты, а также 61 минуту, 25 часов и пр. И хуже всего, что некоторые разработчики, как у нас выражаются, «с фантазией», этим вот всем пользуются. Хорошо что редко :)
>разумное рац. предложение, внедрю, когда выдастся свободное время, спасибо!
Ну да, этож позволяет отмечать интервал не бинарным свойством свободен/занят, а скажем «я тут буду читать книжку, но в принципе для встреч свободен».
Э, всем? Это вообще не они. Тут речь про шкалы времени, и отрезки на них, графа тут может и не быть, и задачи решаются другие — приведенная задача со стоматологом это типовой пример планирования митинга — есть шкалы свободного и занятого времени участников, включая комнату для переговоров. И надо их всех совместить, чтобы все участники могли, и комната была свободна.
К сожалению, ни один из известных мне языков программирования не предоставляет возможности определить это программно.

Может я что-то не понимаю, можете попробовать изучить SQL, — вроде как это стандартная задача из не очень сложных. К примеру, у вас таблица начал и окончаний интервалов занятости лиц и параметром задано значение длительности встречи. Вам надо выбрать все окончания занятости лица 1 (врача), для которых,
— его самое близкое сверху начало занятости будет отстоять вверх на величину большую длительности встречи;
— самое близкое сверху к нему начало интервала занятости лица 2 (вы) будет также отстоять вверх на величину большую длительности встречи и посередине не будет окончания занятости лица 2.
можете попробовать изучить SQL

Спасибо, откажусь. Я его еще не настолько забыл, чтобы изучать заново.


К примеру, у вас таблица [...]

К примеру, у меня вообще нет базы данных.


Вам надо выбрать все окончания занятости [...]

Не только. Например, мне нужно добавить 5 ×​ 31_557_600 секунд к сегодняшней дате, игнорируя специально заданные «праздники» и все выходные (в моем решении задается стримом). И получить точное значение DateTime, с учетом таймзоны в Сиднее, Австралия.


Или мне нужно объединить занятые слоты дантиста с государственными праздниками Каталонии.


Или мне нужно выбрать первый после первого января 2037 года слот продолжительностью в один час, в который свободны все вот эти 10 человек, комната, канал связи, и который пересекается с рабочим временем в таймзоне America/New_York.

К примеру, у вас таблица
К примеру, у меня вообще нет базы данных.

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

Не только. Например, мне нужно добавить 5 ×​ 31_557_600 секунд к сегодняшней дате, игнорируя специально заданные «праздники» и все выходные (в моем решении задается стримом). И получить точное значение DateTime, с учетом таймзоны в Сиднее, Австралия.

Или мне нужно объединить занятые слоты дантиста с государственными праздниками Каталонии.

Или мне нужно выбрать первый после первого января 2037 года слот продолжительностью в один час, в который свободны все вот эти 10 человек, комната, канал связи, и который пересекается с рабочим временем в таймзоне America/New_York.

¡No passaran, camarada! Российский Крым приветствует свободную реcпублику Каталония! Возвращаясь к SQL, вы всерьез полагаете (dangling participle), что упомянутые вами нюансы запросов недоступны для SQL. Поправьте меня, если я не прав, но я привык думать, что любой SQL-related джун вам с легкостью отчебучит и не такое.
Данные ведь как-то храните и каким-то образом же обрабатываете.

Нет, не храню. Это микросервис, который отвечает по API на запросы. Весь in-memory.

Подскажите, пожалуйста, почему у меня может не работать ссылка:
«Итак, встречайте Tempus!»

Комп обычный, другие сайты работают… В каких настройках мне надо порыться?

Я лет 25 назад сделал свою библиотеку для работы с календарными интервалами для научных расчетов (она до сих пор используется). Но — на фортране. Одно время было желание как-то превратить этот проект в Open Source, но недостаток мозгов и отсутствие вменяемого английского не позволили сделать даже первый шаг в эту сторону :-((( А сейчас уже и смысла нет, очевидно.
Но посмотреть функционал Вашей библиотеки хочется. Хотя бы для того, чтобы добавить в свой пакет что-то полезное.
извиняюсь, что просмотрел по диагонали, но учтена возможность смены времени зимнее/летнее внутри интервала?
Только полноправные пользователи могут оставлять комментарии. Войдите, пожалуйста.