首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么datetime.utcnow()和datetime.now(时区(UTC))有区别?

为什么datetime.utcnow()和datetime.now(时区(UTC))有区别?
EN

Stack Overflow用户
提问于 2017-09-02 22:58:51
回答 2查看 906关注 0票数 0

从下面的片段中可以看到,这两个方法之间有一个小时的差异。原因是什么?

代码语言:javascript
复制
from datetime import datetime
from pytz import timezone
import time

def timestamp2date(timestamp):
    # function converts a UTC timestamp into Europe/Zurich Gregorian date
    DATE_TIME_FORMAT = "%Y-%m-%d %H:%M:%S"
    utcTimeStamp = datetime.fromtimestamp(int(timestamp)).replace(tzinfo=timezone('UTC'))
    return utcTimeStamp.astimezone(timezone('Europe/Zurich')).strftime(DATE_TIME_FORMAT)

timeStampUTC_1 = time.mktime(datetime.utcnow().timetuple())
print(timeStampUTC_1)
print(timestamp2date(timeStampUTC_1))
timeStampUTC_2 = time.mktime(datetime.now(timezone('UTC')).timetuple())
print(timeStampUTC_2)
print(timestamp2date(timeStampUTC_2))
print(timeStampUTC_2 - timeStampUTC_1)

# 1504385450.0
# 2017-09-03 00:50:50   this the right time
# 1504389050.0
# 2017-09-03 01:50:50
# 3600.0
EN

回答 2

Stack Overflow用户

发布于 2017-09-03 02:10:30

原因是,如果datetime.timetuple()没有偏移感知,则设置dst=-1,而当偏移感知时,设置dst=0 or 1

从文件中:

结果的tm_isdst标志是根据dst()方法设置的:tzinfo is Nonedst()返回Nonetm_isdst设置为-1;否则,如果dst()返回非零值,tm_isdst设置为1;否则tm_isdst设置为0

代码语言:javascript
复制
In []:
datetime.utcnow()
Out[]:
datetime.datetime(2017, 9, 2, 23, 9, 12, 715042)

In []:
print(datetime.utcnow().dst())
Out[]:
None

In []:
datetime.now(timezone('UTC'))
Out[]:
datetime.datetime(2017, 9, 2, 23, 9, 15, 856983, tzinfo=<UTC>)

In []:
datetime.now(timezone('UTC')).dst()
Out[]
datetime.timedelta(0)

In []:
datetime(2017, 9, 2, 23, 9, 15, 856983).timetuple()
Out[]:
time.struct_time(tm_year=2017, tm_mon=9, tm_mday=2, tm_hour=23, tm_min=9, 
                 tm_sec=15, tm_wday=5, tm_yday=245, tm_isdst=-1)
                                                             ^^
In []:
datetime(2017, 9, 2, 23, 9, 15, 856983, timezone('UTC')).timetuple()
Out[]:
time.struct_time(tm_year=2017, tm_mon=9, tm_mday=2, tm_hour=23, tm_min=9, 
                 tm_sec=15, tm_wday=5, tm_yday=245, tm_isdst=0)
                                                             ^

这将改变time.mktime()生成的time.mktime()生成的-1,因为mktime处理-1未知并使用本地时间,因此可以计算dst=1,因此它们可能有1小时不同(3600s):

代码语言:javascript
复制
In []:
time.mktime(datetime(2017, 9, 2, 23, 9, 15, 856983).timetuple())
Out[]:
1504411755.0

In []:
time.mktime(datetime(2017, 9, 2, 23, 9, 15, 856983, timezone('UTC')).timetuple())
Out[]:
1504415355.0
票数 1
EN

Stack Overflow用户

发布于 2017-09-05 11:32:41

这是我进一步探索与夏令时标志相关的时区概念的结果。代码非常简单。

为了总结结果,有一种正确的方法来处理日期/时间信息:

  1. 日期/时间对象必须本地化。
  2. 如果本地化正确,则日期/时间对象显示正确的夏令时信息。
  3. 这反映在您将本地化的日期/时间对象转换为UTC日期/时间对象时,根据定义,该对象与DST无关。
  4. 当您访问股票或货币历史分钟汇率API时,所有这些注意事项都特别相关。

代码:

代码语言:javascript
复制
from datetime import datetime
from pytz import timezone
import time

print("---- Winter time (CET=Central European Time) ----")
dateStr = "2014-02-28 22:28:15"
datetimeObjUnlocalized = datetime.strptime(dateStr, "%Y-%m-%d %H:%M:%S")
print('UNL: ' + datetimeObjUnlocalized.strftime("%Y-%m-%d %H:%M:%S %Z%z"))
print('     datetimeObjUnlocalized-->tm_isdst=' + str(datetimeObjUnlocalized.timetuple()[8]))
datetimeObjZH = timezone('Europe/Zurich').localize(datetimeObjUnlocalized)
print('ZH:  ' + datetimeObjZH.strftime("%Y-%m-%d %H:%M:%S %Z%z"))
print('     datetimeObjZH-->tm_isdst=' + str(datetimeObjZH.timetuple()[8]))
print("UTC: " + datetimeObjZH.astimezone(timezone('UTC')).strftime("%Y-%m-%d %H:%M:%S %Z%z"))

print("\n---- Summer time (CEST=Central European Summer Time) ----")
dateStr = "2014-06-28 22:28:15"
datetimeObjUnlocalized = datetime.strptime(dateStr, "%Y-%m-%d %H:%M:%S")
print('UNL: ' + datetimeObjUnlocalized.strftime("%Y-%m-%d %H:%M:%S %Z%z"))
print('     datetimeObjUnlocalized-->tm_isdst=' + str(datetimeObjUnlocalized.timetuple()[8]))
datetimeObjZH = timezone('Europe/Zurich').localize(datetimeObjUnlocalized)
print('ZH:  ' + datetimeObjZH.strftime("%Y-%m-%d %H:%M:%S %Z%z"))
print('     datetimeObjZH-->tm_isdst=' + str(datetimeObjZH.timetuple()[8]))
print("UTC: " + datetimeObjZH.astimezone(timezone('UTC')).strftime("%Y-%m-%d %H:%M:%S %Z%z"))

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/46018931

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档