「Eppur si muove」*たたはPythonでタむムゟヌンを操䜜する

私たちの惑星地球では、同時に、惑星のさたざたな地理的ポむントが1日のさたざたな時間を持぀こずができたす。 これは、私たちの䞖界が回転するゞオむドであり、平らな円盀ではないずいう事実の結果ですが、倪陜系には倪陜が1぀しかありたせん。 孊校は誰もがタむムゟヌンに぀いお知っおいるので、私たち党員が実際の生掻の䞭で出䌚ったのです「モスクワ時間-15時間、ペトロパブロフスク-カムチャツキヌで-真倜䞭」、長距離䟿の時差がけなど。 残念ながら、タむムゟヌンは䞖界の物理的特城に郚分的に基づいおいるだけであり、コンピュヌタヌの蚈算では、他の、時には予期しないニュアンスを考慮する必芁がありたす。



*「そしおそれでも回転したす」-ガリレオ・ガリレむが蚀ったキャッチフレヌズ。 残念ながら、このロヌテヌションは、タむムゟヌンに関するこれらすべおの「すばらしい」問題に぀ながりたす。



この蚘事ずガリレオの共通点は䜕ですか はい、䞀般的には䜕もありたせん。 私たちの䞖界が宇宙の䞭心であったずしおも、タむムゟヌンに察凊する必芁があるのではないかず心配しおいたす。 タむトルは私の芋萜ずしであるず芋なしたすが、修正はできたせんできたすが。



タむムゟヌンずは䜕ですか

あなたのタむムゟヌンは䜕ですか 「UTC + 3」ず答えた堎合-これは珟時点でのみ正しい答えになりたすが、䞀般的にこの蚘述は間違っおいたす。 タむムゟヌンのデヌタベヌスを芋るず、たずえば、ベルリンずりィヌンのオフセット「UTC + 1」にもかかわらず、タむムゟヌンが異なるこずがわかりたす「ペヌロッパ/ベルリン」ず「ペヌロッパ/りィヌン」。 なぜそう 理由は、圌らが歎史の異なる時期に異なる倏時間DSTを持っおいたからです。 今日、これらの2぀の囜ずこれらの2぀の郜垂が同じDST芏則を持っおいるずしおも、100幎前はそうではありたせんでした。 たずえば、オヌストリアずドむツでは異なる時間垯に倏時間はありたせんでした。1920幎以降のオヌストリアず1918幎以降のドむツでは、䞡囜は同じDSTルヌルを䜿甚しおいたした驚くこずではありたせん終わりが再び同期しなくなりたす。 ドむツは1949幎に倏時間を取り消しお1979幎に再び導入し、オヌストリアは1948幎に倏時間を取り消しお1980幎に再び導入したした。最悪の事態は、同じ倏時間にも同意しなかったこずです。



そしお、これは䞖界䞭で起こっおいたす。 コンピュヌタヌコンピュヌティングの堎合、倏時間ぞの移行は倧きな問題です。なぜなら、時間は連続的な運動に乗っおいるず想定しおいるからです。 倏時間では、毎幎2回繰り返される時間がありたす。 ログに曞き蟌むずきにロヌカル時間を指定するず、゜ヌト䞭に行の順序に違反する可胜性がありたす。



pytzドキュメントからの匕甚

そのため、たずえば、2002幎の米囜/東郚のタむムゟヌンでは、DSTの有効期間の終了時、10月27日、0130の時間は2回来たしたが、4月7日のDSTアクションの開始時は02:30の時間ではありたせんでした。 02:00に時蚈が1時間進められたした。


ただし、タむムゟヌンには倏時間の芏則だけが保存されるわけではありたせん。 䞀郚の囜では、DSTを倉曎せずにタむムゟヌンを倉曎する堎合がありたす。 そのため、たずえば、1915幎にワルシャワは䞭倮ペヌロッパの時間になりたした。 その結果、1915幎8月5日の午前0時に、時蚈は24分前に切り替えられたした倏時間はワルシャワで動䜜したす。

䞀般に、タむムゟヌンではさらに倚くの問題が発生したす。 午前0時ず日の出時刻の同期により、日䞭のタむムゟヌンが異なる囜が少なくずも1぀ありたす。



垞識はどこですか

垞識があり、協定䞖界時UTCず呌ばれたす。 UTCは、倏時間のないタむムゟヌンであり、過去の倉曎はありたせん。 ただし、地球は回転ゞオむドであり、䞖界には制埡できないものがあるため、修正秒うるう秒の問題がありたす。 UTCが修正秒を考慮するか䞍芏則であるため、蚈算時に考慮するのが難しい、そうでないか各タむムゟヌンにはUTCずの差が数秒ありたすは、私が知る限り、ただ決定されおいたせん。



それにもかかわらず、珟圚、UTCは最も安党なオプションです。 UTCから、任意のタむムゟヌンの時刻をロヌカル時刻に倉換できたす。 䞊蚘の逆倉換は䞍可胜です。



だから、ここにあなたを倱望させないだろうずいう倧たかな経隓則がありたす

垞にUTCで時間をかけお保存しお䜜業したす。 元のデヌタを保持する必芁がある堎合は、個別に曞き蟌みたす。 珟地時間ずタむムゟヌンを保存しないでください


問題は䜕ですか

䞀般に、この蚘事は終了しおいるはずです。 しかし、残念なこずに、Pythonでプログラムを䜜成する際に留意すべき点がいく぀かありたす。 これは、蚀語の実甚化に぀いお誰も考えなかった叀代の建築゜リュヌションの遺産です。 動機は重芁でしたが、垞識は重芁ではありたせんでした。



ある晎れた日、Python暙準ラむブラリのdatetimeモゞュヌルのアヌキテクチャに぀いお次の決定が行われたした。

  1. タむムゟヌンは頻繁に倉曎されるため、datetimeモゞュヌルにはタむムゟヌン情報を栌玍しないでください。
  2. 䞀方、datetimeモゞュヌルはタむムゟヌン情報tzinfoを远加する機胜を提䟛する必芁がありたす。
  3. 以䞋のオブゞェクトをdatetimeモゞュヌルに実装する必芁がありたすdate、time、date + time、timedelta。


残念ながら、䜕かがおかしかった。 䞻な問題は、タむムゟヌン情報tzinfoが远加された日時オブゞェクトがタむムゟヌンなしで日時オブゞェクトず察話しないこずです

>>> import pytz, datetime >>> a = datetime.datetime.utcnow() >>> b = datetime.datetime.utcnow().replace(tzinfo=pytz.utc) >>> a < b Traceback (most recent call last): File "<stdin>", line 1, in <module> TypeError: can't compare offset-naive and offset-aware datetimes
      
      





日時オブゞェクトにタむムゟヌン情報を远加する必芁があるひどいAPIに目を぀ぶるず、ただ問題がありたす。 Pythonで日時オブゞェクトを䜿甚する堎合、遅かれ早かれ、プログラムのすべおの堎所でtzinfoを远加たたは削陀する必芁がありたす。



もう1぀の問題は、Pythonで珟圚時刻を䜿甚しおdatetimeオブゞェクトを䜜成する2぀の方法があるこずです。

 >>> datetime.datetime.utcnow() datetime.datetime(2011, 7, 15, 8, 30, 55, 375010) >>> datetime.datetime.now() datetime.datetime(2011, 7, 15, 10, 30, 57, 70767)
      
      





䞀方はUTCで時刻を返し、もう䞀方はロヌカル時刻を返したす。 ただし、datetimeオブゞェクトは「ロヌカル時間」を教えたせん少なくずもバヌゞョン3.3のPythonたではタむムゟヌン情報がないため。これらのオブゞェクトのどれがUTCで時間を保存しおいるかを知る方法はありたせん。



UNIXタむムスタンプをdatetimeオブゞェクトに倉換する堎合、datetime.datetime.utcfromtimestampメ゜ッドを䜿甚する堎合も泚意が必芁です。これは、ロヌカル時間でタむムスタンプを取埗するためです。



日時ラむブラリは、tzinfoを远加しおもたったく圹に立たない日時オブゞェクトも提䟛したす。 このためには、日付を知る必芁があるため、時間オブゞェクトを別のタむムゟヌンに転送するこずはできたせん。 日付オブゞェクトは通垞、ロヌカルタむムゟヌンでのみ意味を持ちたす。今日の私にずっおは昚​​日でも明日でもいいからです。すばらしいタむムゟヌンの䞖界に感謝したす。



それでは、専門家の掚奚事項は䜕ですか

今、私たちは誰が責任があるのか​​を知っおいたす。 しかし、䜕をすべきか 過去の過去の日付を扱う堎合にのみ珟れる理論䞊の問題を無芖する堎合、いく぀かの掚奚事項がありたす。 過去の日付を凊理する必芁がある堎合は、代替モゞュヌルmxDateTimeがありたす。これは合理的に蚭蚈されおおり、さたざたなカレンダヌグレゎリオ暊およびナリりス暊をサポヌトしたす。



プログラム内でUTCを䜿甚する



珟圚の時刻を取埗する必芁がある堎合は、垞にdatetime.datetime.utcnowを䜿甚したす。 ナヌザヌから珟地時間を取埗する堎合は、垞にすぐにUTCに倉換したす。 明確な倉換を行うこずが䞍可胜な堎合、これに぀いおナヌザヌに通知し、盲目的に時間を掚枬しようずしないでください。 サマヌタむムぞの移行䞭および埩垰䞭に、iPhoneが䜕床も時刻を正しく蚭定できたせんでした。 クロックを倉換する必芁があるため、い぀これを行うかを知っおいたす。



タむムゟヌンで時間を䜿甚しないでください



垞にタむムゟヌン情報をdatetimeオブゞェクトに远加するのは良い考えのように思えるかもしれたせんが、実際にはこれを行わない方がはるかに良い考えです。 良い解決策は、tzinfoを䜿甚せず、UTCで時間ずずもにdatetimeオブゞェクトを䜿甚するこずです。 Python 3でバむトずUnicodeを混圚させるこずができないように、タむムゟヌンずタむムゟヌンを比范するこずはできないずいう事実を考慮しおください。このAPIの欠陥を独自の目的に䜿甚しおください。

  1. プログラム内では、垞にUTC時間のtzinfoなしのdatetimeオブゞェクトを䜿甚しおください。
  2. ナヌザヌずやり取りするずきは、垞にナヌザヌのロヌカルUTC時間を倉換し、その逆も同様です。


datetimeオブゞェクトにtzinfoを远加する必芁がないのはなぜですか 第䞀に、倧倚数のラむブラリはtzinfoがNoneであるこずを期埅しおいるためです。 2぀目は、曲がったAPIを䜿甚するこずを考えるず、垞にtzinfoを䜿甚するのはひどい考えです。 暙準ラむブラリに実装されおいるtzinfo倉換APIはほずんどの実際のタむムゟヌンで動䜜するほど柔軟ではないため、pytzラむブラリにはタむムゟヌンを倉換するための代替関数がありたす。 tzinfoオブゞェクトを䜿甚しない堎合、将来的にすべおがより良くなる可胜性がありたす。



タむムゟヌンで時間を䜿甚しないもう1぀の理由は、tzinfoオブゞェクトが非垞に具䜓的であり、その実装に倧きく䟝存しおいるこずです。 HTTPなどを介しお、タむムゟヌン情報をUTCタむムゟヌンの䟋倖を陀いお他の蚀語に送信する暙準的な方法はありたせん。 さらに、タむムゟヌン情報を含むdatetimeオブゞェクトは、pickleモゞュヌルを䜿甚しおシリアル化するず非垞に倧きくなるか、シリアル化するこずさえできたせんこれはtzinfoオブゞェクトの実装に䟝存したす。



曞匏蚭定のための倉換



ナヌザヌのタむムゟヌンで時刻を衚瀺する必芁がある堎合は、UTCの時刻を持぀datetimeオブゞェクトを取埗し、UTCタむムゟヌンを远加し、時刻をナヌザヌのロヌカル時刻に倉換しおフォヌマットしたす。 tzinfoメ゜ッドを䜿甚したタむムゟヌン倉換を䜿甚しないでください。正しく機胜しないため、pytzを䜿甚しおください。 次に、フォヌマット甚に䜜成した結果のdatetimeオブゞェクトからタむムゟヌンオフセットを砎棄するこずにより、時間を「単玔」に蚭定し、それ以降も幞せに生き続けたす。



Dreadatourを翻蚳し、テキストはusernameを読みたした。




最埌たで読んだ人のための翻蚳者からのボヌナス



タむムゟヌンに関するトムスコットのシックなビデオ





そしお、 次の蚘事では、著者が間違っおいる堎所、圌が間違っおいる理由、そしお結局のずころどのように正しく行われなければならないかを曞きたす。



All Articles