Дата Математика - Как избежать DST - PullRequest
0 голосов
/ 05 мая 2018

Я делаю некоторые операции с датами. Я проверил учебники, чтобы увеличить дату на один день, чтобы убедиться, что дата конвертируется в «мс», и просто добавляю «86400000». Проблема появляется, когда я передаю даты изменения DST.

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

Я пытался изменить

"timeZone": "Europe/London"

в appscript.json для "Japan" (они не используют DST), но ничего не произошло.

Есть ли простое решение этой проблемы или мне нужно сделать какой-нибудь обходной код или дополнительные условия? Заранее спасибо!

РЕДАКТИРОВАТЬ: Это часть кода, где я проверяю и сравниваю даты.

     var dayMS = 24*60*60*1000;
      var check_date = variables_sheet.getRange(2,1).getValue().getTime(); //get starting date
  for (var i=1; i<=length; i++) {
    if (check_date == Dates_Table[i][0].getTime())
    {
      sum = sum + Flow_Table[i][0]; //make a sum of values from the same date
    }
    else {
      target_sheet.appendRow([new Date(check_date), "B", "C", sum, Balance_Table[i-1][0]]); //write consolidated days with sum
      check_date = check_date+dayMS;   //increment days   
      i--;     //go back
      sum = 0; //reset sum

    }

  };

1 Ответ

0 голосов
/ 10 мая 2018

Из заголовка вашего вопроса «как избежать DST» - нельзя. Местное время во многих часовых поясах имеет летнее время. Вы не можете избежать этого - вместо этого вы должны использовать API, которые его учитывают.

Поскольку вы присвоили dayMS равным 24 часам, вы работаете против этого. Дни с типичными переходами DST на 1 час могут длиться 23 или 25 часов. Также возможно иметь переходы продолжительностью 30 минут, которые могут быть вызваны переходом на летнее время (хотя бы в одном часовом поясе) или просто из-за изменения стандартного смещения часового пояса.

Таким образом, при вычислении дней не предполагайте, что они являются фиксированной единицей времени. Они отличаются так же, как каждый месяц имеет разное количество дней, и как високосные годы имеют на один день больше, чем обычные годы. Подумайте: «дата математика! = Время математика».

В приведенном выше коде нет необходимости звонить getTime() никогда. Просто сохраните значения как Date объекты и используйте механизм, указанный в комментариях к вопросу. Другими словами, после удаления всех .getTime() вхождений, продвиньте дату с помощью:

check_date.setDate(check_date.getDate() + 1 ));

Это изменяет переменную check_date, поэтому нет назначения.

Это в основном нормально, но есть одна проблема с этим подходом, заключающаяся в том, что если результирующее значение попадает прямо в середину «разрыва» (такого как значение, созданное переходом DST с упругим движением вперед), оно будет скорректирована до некоторой другой законной стоимости. В зависимости от реализации приложения-скрипта Google, он может скорректироваться вперед или скорректироваться в обратном направлении (я не уверен, какой из них не в руки). Это может быть хорошо для одного случая, но я сомневаюсь, что вы захотите использовать это скорректированное значение в будущем. Таким образом, может быть безопаснее отслеживать целое число дней от базовой даты в отдельной переменной (скажем, x) - тогда вместо увеличения check_date один день за раз вы будете воссоздавать check_date каждый пройти цикл и добавить x дней.

...