Niespójna strefa czasowa analizy daty i godziny w Pythonie

Nov 23 2020

Kiedy uruchamiam poniższe w Pythonie 3.X

import datetime

DATE_TS_FORMAT = '%Y-%m-%d %H:%M:%S.%f %Z'

date_ts = datetime.datetime(2019, 1, 2, 3, 4, 5, tzinfo=datetime.timezone.utc)
date_ts = date_ts.strftime(DATE_TS_FORMAT)
print(date_ts)
date_ts = datetime.datetime.strptime(date_ts, DATE_TS_FORMAT)
date_ts = date_ts.strftime(DATE_TS_FORMAT)
print(date_ts)

dostaję

2019-01-02 03:04:05.000000 UTC
2019-01-02 03:04:05.000000 

Dlaczego informacje o strefie czasowej zniknęły i jak mogę rozwiązać ten problem?

Odpowiedzi

2 MrFuppes Nov 24 2020 at 07:13

Rzeczywiście niespójne ... Chodzi o to, że %Zsprawia , że strptime akceptuje określone ciągi (GMT, UTC i dowolną wartość w time.tzname - docs ), ale tak naprawdę nic z tego nie robi. Dawny:

from datetime import datetime

s = "2019-01-02 03:04:05.000000 UTC"
dt = datetime.strptime(s, '%Y-%m-%d %H:%M:%S.%f %Z')

print(repr(dt))
# datetime.datetime(2019, 1, 2, 3, 4, 5)

Wynikowy obiekt daty i godziny jest naiwny; nie ma już śladu UTC.

Aby uwzględnić to zachowanie, można przetworzyć obiekt datetime, na przykład

if "UTC" in s: 
    dt = dt.replace(tzinfo=timezone.utc)

(co moim zdaniem jest trochę bolesne ...) lub zastąp „UTC” czymś, co %zanalizuje do UTC 1 ,

dt = datetime.strptime(s.replace("UTC", "+00:00"), '%Y-%m-%d %H:%M:%S.%f %z')

print(repr(dt))
# datetime.datetime(2019, 1, 2, 3, 4, 5, tzinfo=datetime.timezone.utc)

(co wydaje mi się trochę brzydkie ...) lub użyj odpowiedniego parsera, np

from dateutil.parser import parse

dt = parse(s)

print(repr(dt))
# datetime.datetime(2019, 1, 2, 3, 4, 5, tzinfo=tzutc())

print(dt.strftime('%Y-%m-%d %H:%M:%S.%f %Z'))
# 2019-01-02 03:04:05.000000 UTC

(co będzie nieco wolniejsze, jeśli problemem jest wydajność ...).


1 IMO, to również jest niespójne; „+00: 00” może być również przesunięciem czasu UTC w pewnej strefie czasowej, w której w tym czasie przesunięcie względem UTC wynosi 0 godzin ...