当前位置: 首页 > 面试题库 >

使用datetime在python中获取UTC时间戳

曾修真
2023-03-14
问题内容

有没有一种方法可以通过指定日期来获取UTC时间戳?我期望的是:

datetime(2008, 1, 1, 0, 0, 0, 0)

应该导致

 1199145600

创建朴素的datetime对象意味着没有时区信息。如果我查看datetime.utcfromtimestamp的文档,则创建UTC时间戳意味着会忽略时区信息。因此,我猜想,创建一个简单的datetime对象(如我所做的那样)会导致UTC时间戳。然而:

then = datetime(2008, 1, 1, 0, 0, 0, 0)
datetime.utcfromtimestamp(float(then.strftime('%s')))

结果是

2007-12-31 23:00:00

datetime对象中是否还存在任何隐藏的时区信息?我究竟做错了什么?


问题答案:

天真datetime与意识datetime

默认datetime对象被称为“天真”的:它们保留时间信息而没有时区信息。可以将朴素的名字datetime当作一个+4没有明确来源的相对数字(即:)(实际上,您的来源在整个系统边界中都是常见的)。

相比之下,请考虑将意识datetime看作8是全世界共有的绝对数(即:)。

没有时区信息,您 将无法
将“原始”日期时间转换为任何非原始时间表示形式( +4如果我们不知道从哪里开始,目标会在哪里?)。这就是为什么您没有 datetime.datetime.toutctimestamp()方法的原因。(参见: http
//bugs.python.org/issue1457227)

要检查您datetime dt是否天真,请检查dt.tzinfo,如果是None,则表示天真:

datetime.now()        ## DANGER: returns naïve datetime pointing on local time
datetime(1970, 1, 1)  ## returns naïve datetime pointing on user given time

我的约会时间很晚,该怎么办?

您必须根据自己的具体情况做出假设:您必须问自己的问题是:您是否datetime在UTC上?还是当地时间?

  • 如果您使用的是UTC (没有麻烦):

    import calendar
    

    def dt2ts(dt):
    “”“Converts a datetime object to UTC timestamp

    naive datetime will be considered UTC.
    
    """
    
    return calendar.timegm(dt.utctimetuple())
    
  • 如果您不使用UTC ,欢迎来到地狱。

datetime在使用前一个功能之前,您必须先将其退回给他们想要的时区,以使其天真。

您将需要 时区的名称, 以及在生成目标原始日期时间时 有关DST是否生效 的信息(关于DST的最后信息对于角落情况是必需的):

    import pytz     ## pip install pytz

mytz = pytz.timezone('Europe/Amsterdam')             ## Set your timezone

dt = mytz.normalize(mytz.localize(dt, is_dst=True))  ## Set is_dst accordingly

不提供的后果is_dst

is_dst如果在向后放置DST时产生了目标日期时间(例如,通过删除一小时来更改DST时间),则不使用将产生不正确的时间(和UTC时间戳)。

is_dst当然,仅提供错误的遗嘱只会在DST重叠或空洞时生成错误的时间(和UTC时间戳)。而且,如果还提供了不正确的时间,则出现在“空洞”中(由于DST向前移动而永远不存在的时间),is_dst将解释如何考虑此虚假时间,这是唯一在
.normalize(..)此处实际做些事情的情况,因为它将随后将其转换为实际有效时间(如果需要,请更改datetime和DST对象)。请注意,.normalize()不需要在末尾具有正确的UTC时间戳,但是如果您不喜欢在变量中使用假时间的想法,尤其是在其他地方重用此变量时,建议您这样做。

避免使用以下内容
:(参见:使用pytz的Datetime时区转换)

    dt = dt.replace(tzinfo=timezone('Europe/Amsterdam'))  ## BAD !!

为什么?因为.replace()tzinfo不考虑目标时间的情况下盲目更换DST会选择一个不良的DST对象。而.localize()使用目标时间和is_dst提示来选择正确的DST对象。

OLD错误答案 (感谢@JFSebastien提出):

希望您可以很容易地在创建朴素datetime对象时猜测时区(您的本地来源),因为它与系统配置有关,希望您不会在朴素日期时间对象创建和获取日期之间进行更改。
UTC时间戳。这个技巧可以用来提出一个 不完善的 问题。

通过使用time.mktime我们可以创建一个utc_mktime

def utc_mktime(utc_tuple):
    """Returns number of seconds elapsed since epoch

    Note that no timezone are taken into consideration.

    utc tuple must be: (year, month, day, hour, minute, second)

    """

    if len(utc_tuple) == 6:
        utc_tuple += (0, 0, 0)
    return time.mktime(utc_tuple) - time.mktime((1970, 1, 1, 0, 0, 0, 0, 0, 0))

def datetime_to_timestamp(dt):
    """Converts a datetime object to UTC timestamp"""

    return int(utc_mktime(dt.timetuple()))

您必须确保datetime在创建对象时所在的时区与创建对象时所在的时区相同datetime

最后一个解决方案是不正确的,因为它假设从现在开始的UTC偏移量与从EPOCH到UTC的偏移量相同。
对于许多时区而言,情况并非如此(夏令时(DST)偏移量是一年中的特定时间)。



 类似资料:
  • 问题内容: 我想获取UTC时区的时间。所以我写了代码: 问题是输出显示了我的PST时间(我的本地时区)。我需要它来输出UTC时间,以便将其存储在数据库中。 问题答案:

  • 我想要得到UTC时区的时间。所以我写了代码: 问题是输出显示了PST(我的本地时区)中的时间。我需要它以UTC的形式输出时间,这样我就可以把它存储在我的数据库中。

  • 问题似乎在这个文件中:https://github.com/brianc/node-postgres/blob/master/lib/types/textparsers.js 如果从Postgres返回的日期字符串没有指定时区(例如或),那么它只会构造一个JavaScript日期对象,我相信它只会包括本地时区。

  • 问题内容: 获取当前UTC时间的功能是什么。我已经尝试使用System.getCurrentTime,但是我得到了设备的当前日期和时间。 谢谢 问题答案: 确实会提供自1970年1月1日UTC以来的毫秒数。您看到本地时间的原因可能是因为您在使用实例之前将其转换为字符串。您可以使用s 在任何时区将s 转换为s: 另请参阅此相关问题。

  • 问题内容: 在编写Web应用程序时,将 所有 日期时间(服务器端)存储在数据库中作为UTC时间戳是有意义的。 当我发现您无法在JavaScript中对时区进行操作方面自然无法做到这一点时,我感到非常惊讶。 我稍微扩展了Date对象。这个功能有意义吗?基本上,每次我向服务器发送任何内容时,都会使用该功能格式化时间戳记。 您在这里看到任何重大问题吗?还是从另一个角度解决问题? 在我看来,这有点令人费解

  • 我选择“无时区”是因为我知道我的应用程序使用的所有时间戳总是UTC。就我得到的文档而言,“with timestamp”的唯一区别是,我可以提供其他时区的值,然后将其转换为UTC。然而,我想避免这样的自动转换,因为如果我知道我的值是UTC,它们几乎没有任何好处。 当我在测试表中添加新记录并使用pgAdmin查看表的内容时,我可以看到插入日期已正确地保存为UTC格式。 但是,当我尝试使用JDBC选择