我们可以用time.tzname
获取本地时区的名称,但该名称不兼容pytz.timezone
。
事实上,返回的名称time.tzname
是模糊的。 这个方法返回('CST', 'CST')
在我的系统,但“CST”可以指出了四个时区:
- 中央时区(北美) - 在北美地区的中央时区观察
- 中国标准时间
- Chungyuan标准时间 - 术语“Chungyuan标准时间”,现在很少在台湾使用
- 澳大利亚中部标准时间(ACST)
我们可以用time.tzname
获取本地时区的名称,但该名称不兼容pytz.timezone
。
事实上,返回的名称time.tzname
是模糊的。 这个方法返回('CST', 'CST')
在我的系统,但“CST”可以指出了四个时区:
tzlocal
模块返回对应于本地时区pytz tzinfo的对象:
import time
from datetime import datetime
import pytz # $ pip install pytz
from tzlocal import get_localzone # $ pip install tzlocal
# get local timezone
local_tz = get_localzone()
# test it
# utc_now, now = datetime.utcnow(), datetime.now()
ts = time.time()
utc_now, now = datetime.utcfromtimestamp(ts), datetime.fromtimestamp(ts)
local_now = utc_now.replace(tzinfo=pytz.utc).astimezone(local_tz) # utc -> local
assert local_now.replace(tzinfo=None) == now
它在夏令时转换工作,即使本地时间可能是模糊的。
local_tz
也适用于过去的日期即使UTC本地时区偏移是在不同的时间。 dateutil.tz.tzlocal()
基溶液在这种情况下例如出现故障时,在欧洲/莫斯科时间(从2013示例):
>>> import os, time
>>> os.environ['TZ'] = 'Europe/Moscow'
>>> time.tzset()
>>> from datetime import datetime
>>> from dateutil.tz import tzlocal
>>> from tzlocal import get_localzone
>>> dateutil_tz = tzlocal()
>>> tzlocal_tz = get_localzone()
>>> datetime.fromtimestamp(0, dateutil_tz)
datetime.datetime(1970, 1, 1, 4, 0, tzinfo=tzlocal())
>>> datetime.fromtimestamp(0, tzlocal_tz)
datetime.datetime(1970, 1, 1, 3, 0, tzinfo=<DstTzInfo 'Europe/Moscow' MSK+3:00:00 STD>)
dateutil返回错误 UTC + 4偏移,而不是正确UTC + 3 1970-01-01。
对于那些碰到这个在2017年 dateutil.tz.tzlocal()
仍然是断开的。 上面的例子现在的工作,因为当前的UTF偏移是UTC + 3在莫斯科(即意外等于UTC从1970年的偏移)。 为了证明我们可以选择一个日期时UTC偏移量为UTC + 4的错误:
>>> import os, time
>>> os.environ['TZ'] = 'Europe/Moscow'
>>> time.tzset()
>>> from datetime import datetime
>>> from dateutil.tz import tzlocal
>>> from tzlocal import get_localzone
>>> dateutil_tz = tzlocal()
>>> tzlocal_tz = get_localzone()
>>> ts = datetime(2014, 6,1).timestamp() # get date in 2014 when gmtoff=14400 in Moscow
>>> datetime.fromtimestamp(ts, dateutil_tz)
datetime.datetime(2014, 5, 31, 23, 0, tzinfo=tzlocal())
>>> datetime.fromtimestamp(ts, tzlocal_tz)
datetime.datetime(2014, 6, 1, 0, 0, tzinfo=<DstTzInfo 'Europe/Moscow' MSK+4:00:00 STD>)
dateutil返回错误 UTC + 3的偏移而不是正确的UTC + 4 2014-06-01。
使用tzlocal
功能从python-dateutil
包 :
from dateutil.tz import tzlocal
localtimezone = tzlocal()
内部,这是使用一个类time.timezone
和time.altzone
(基于开关time.daylight
),但是从用于创建一个合适的时区的对象。
您可以使用它来代替一个pytz
时区。
另一种方法是,以读取来自操作系统代替当前配置的时区,但这种广泛不同于操作系统OS。 在Mac OS X,你需要阅读的输出systemsetup -gettimezone
:
$ systemsetup -gettimezone
Time Zone: Europe/Copenhagen
在Debian和Ubuntu系统中,你可以阅读/etc/timezone
:
$ cat /etc/timezone
Europe/Oslo
在RedHat和direved系统,你需要从阅读它/etc/sysconfig/clock
:
$ grep ZONE /etc/sysconfig/clock
ZONE="Europe/Oslo"
一个非常简单的方法来解决这个问题:
import time
def localTzname():
offsetHour = time.timezone / 3600
return 'Etc/GMT%+d' % offsetHour
更新 :@MartijnPieters说:“这不会与DST /夏令工作。” 因此,如何这个版本?
import time
def localTzname():
if time.daylight:
offsetHour = time.altzone / 3600
else:
offsetHour = time.timezone / 3600
return 'Etc/GMT%+d' % offsetHour
因为Python 3.6,你可以简单地运行naive_datetime.astimezone()
和系统时区将被添加到naive_datetime
对象。
如果不带参数调用(或具有TZ =无)的系统的本地时区被假定为目标时区。 转换后的日期时间实例的.tzinfo属性将被设置为与所述区域名称时区的一个实例,并从OS偏移而获得。
https://docs.python.org/3/library/datetime.html#datetime.datetime.astimezone
例:
>>> import datetime
>>> datetime.datetime.now().astimezone().isoformat(timespec='minutes')
'2018-10-02T13:09+03:00'
我不知道这是否是对你还是没有用,但我认为它回答您更普遍的问题:
如果你是在一个模糊的时区,像一个日期CST
, 简单日期 (蟒蛇3.2+只,抱歉)可以自动搜索,并允许您像喜欢某些国家做的事情。
例如:
>>> SimpleDate('2013-07-04 18:53 CST')
Traceback [...
simpledate.AmbiguousTimezone: 3 distinct timezones found: <DstTzInfo 'Australia/Broken_Hill' CST+9:30:00 STD>; <DstTzInfo 'America/Regina' LMT-1 day, 17:01:00 STD>; <DstTzInfo 'Asia/Harbin' LMT+8:27:00 STD> (timezones=('CST',), datetime=datetime.datetime(2013, 7, 4, 18, 53), is_dst=False, country=None, unsafe=False)
>>> SimpleDate('2013-07-04 18:53 CST', country='CN')
SimpleDate('2013-07-04 18:53 CST')
>>> SimpleDate('2013-07-04 18:53 CST', country='CN').utc
SimpleDate('2013-07-04 10:53 UTC', tz='UTC')
注意如何通过指定一个国家,你减少可能值的范围足以允许转换为UTC。
它是由做了在PyTZ的时区搜索实现的:
>>> SimpleDate('2013-07-04 18:53 CST', country='CN', debug=True)
...
PyTzFactory: Have country code CN
PyTzFactory: Country code CN has 5 timezones
PyTzFactory: Expanded country codes to 5 timezones
PyTzFactory: Expanding ('CST',)
PyTzFactory: Name lookup failed for CST
PyTzFactory: Found CST using Asia/Shanghai
PyTzFactory: Found CST using Asia/Harbin
PyTzFactory: Found CST using Asia/Chongqing
PyTzFactory: Found CST using Asia/Urumqi
PyTzFactory: Found CST using Asia/Kashgar
PyTzFactory: Expanded timezone to 5 timezones
PyTzFactory: New offset 8:00:00 for Asia/Shanghai
PyTzFactory: Known offset 8:00:00 for Asia/Harbin
PyTzFactory: Known offset 8:00:00 for Asia/Chongqing
PyTzFactory: Known offset 8:00:00 for Asia/Urumqi
PyTzFactory: Known offset 8:00:00 for Asia/Kashgar
PyTzFactory: Have 1 distinct timezone(s)
PyTzFactory: Found Asia/Shanghai
...
SimpleDate('2013-07-04 18:53 CST')
最后,回答直接问的问题,它也包装tzlocal,在另一个答案讲到这里,所以会自动完成你所期望的,如果你不给一个时区。 例如,我住在智利,所以
>>> SimpleDate()
SimpleDate('2013-07-04 19:21:25.757222 CLT', tz='America/Santiago')
>>> SimpleDate().tzinfo
<DstTzInfo 'America/Santiago' CLT-1 day, 20:00:00 STD>
给我的语言环境的时区(不明确或没有)。
import pytz
说你有在OBJ列表对象UTC日期时间值的列表。
tz=pytz.timezone('Asia/Singapore')
看看下面的网址,获取相应的时区位置字符串参数是否有Pytz时区的列表?
现在我们的TZ是具有新加坡时间对象
result=[]
for i in OBJ:
i=i+tz.utcoffset(i)
result.append(i)
结果列表对象的各自时区的日期时间值