关于python:datetime with pytz timezone。 不同的偏移量取决于tzinfo的设置方式

datetime with pytz timezone. Different offset depending on how tzinfo is set

本问题已经有最佳答案,请猛点这里访问。

我今天遇到了一个有趣的情况。 谁能解释为什么ts1和ts2的偏移量不同? ts1是一个日期时间对象,可立即识别时区。 ts2是一个日期时间对象,它从时区开始并且替换了tzinfo。 然而,他们最终得到不同的抵消。

1
2
3
4
5
6
7
8
9
>>> from pytz import timezone
>>> EST = timezone('America/New_York')
>>> ts1 = datetime.datetime.now(tz=EST)
>>> ts2 = datetime.datetime.now()
>>> ts2 = ts2.replace(tzinfo=EST)
>>> print ts1
2014-05-16 11:25:16.749748-04:00
>>> print ts2
2014-05-16 11:25:19.581710-05:00


当你调用ts2.replace(tzinfo=EST)时,你得到的tzinfo对象与你用ts1得到的对象不匹配:

1
2
3
4
>>> ts1
datetime.datetime(2014, 5, 16, 11, 51, 7, 916090, tzinfo=<DstTzInfo 'America/New_York' EDT-1 day, 20:00:00 DST>)
>>> ts2
datetime.datetime(2014, 5, 16, 11, 51, 30, 922692, tzinfo=<DstTzInfo 'America/New_York' LMT-1 day, 19:04:00 STD>)

你最终得到LMT而不是EDT。

pytz文档实际上指出,将pytz与标准日期时间对象的tzinfo参数一起使用对于许多时区都不起作用:

Unfortunately using the tzinfo argument of the standard datetime
constructors ''does not work'' with pytz for many timezones.

>>> datetime(2002, 10, 27, 12, 0, 0, tzinfo=amsterdam).strftime(fmt) '2002-10-27 12:00:00 LMT+0020'

It is safe for timezones without daylight saving transitions though,
such as UTC:

>>> datetime(2002, 10, 27, 12, 0, 0, tzinfo=pytz.utc).strftime(fmt) '2002-10-27 12:00:00 UTC+0000'

我不确定为什么第一个有效;也许是因为当最初使用tzinfo对象构造对象时,它实际上不需要转换任何东西。

编辑:

啊,Python文档指出使用datetime.datetime.now()tz arg相当于:

1
EST.fromutc(datetime.utcnow().replace(tzinfo=EST))

这意味着您要从UTC转换,这对pytz是安全的。所以这就是第一个有效的原因。


根据文档,将时区应用于天真日期时间的正确方法是使用localize方法。

1
ts1 = eastern.localize(datetime.datetime.now())

此外,我建议您使用avoid EST作为变量名称,因为它通常是"东部标准时间"的标准,而America/New_York包括"东部标准时间"(EST)和"东部夏令时"(EDT)。