【问题标题】:Convert epoch timestamp to datetime.datetime object将纪元时间戳转换为 datetime.datetime 对象
【发布时间】:2012-11-13 19:03:00
【问题描述】:

我想将一个纪元时间戳(例如,et =1351036517.179364)转换为 datetime.datetime 对象。到目前为止,我已经使用了 time.ctime(et) ,它给了我一个类似“Fri Oct 5 22:20:33 2012”的字符串。

最终,我需要 datetime 对象来计算两个数据点之间的时间差,另一个数据点也是一个 datetime 对象。

谢谢!

【问题讨论】:

  • 时间戳可以直接减去,得到以秒为单位的时间差异。

标签: python datetime epoch


【解决方案1】:

值得记住的是,时间戳没有关联的时区信息Unix time 是明确的 UTC,但以 Unix 风格 时间戳存储本地时间并不罕见。您必须核对已知的参考资料才能确定。


如果您的时间戳已经是 UTC(Unix 时间),您可以使用 Marc B 的建议,即直接减去两个 unix 时间戳,以得到它们之间的差异秒数。 然后,您可能想要创建一个timedelta,这将允许您轻松地使用它来操作datetimes(例如,您可以将时间增量与日期时间相加或相减)。

datetime.timedelta( seconds= n_seconds )


如果您的时间戳是当地时间,请不要直接减去它们,因为您可能会得到不正确的结果。

相反,您应该先使用datetime.fromtimestamp,然后使用attach a timezone to each datetime,然后再减去它们以获得时间增量。

要从 timedelta 转换回秒数,有 timedelta.total_seconds,假设您使用的是 python 2.7。如果您有较早的版本,则必须手动计算,或pip install datetime

【讨论】:

  • 知道了。非常感谢@goncalopp 和 Marc B!
  • 这是错误的。没有“本地时间的unix时间戳”这样的东西。 1351036517.179364 unix 时间戳对应于巴黎的2012-10-24T01:55:17.179363,纽约的2012-10-23T19:55:17.179363。您可以直接子构造时间戳——它们是“自纪元以来的秒数”(如果我们忽略 SI 秒和平均太阳 (UT1) 秒之间的差异,则经过的秒数。换句话说,忽略闰秒)。
  • @J.F.Sebastian 从技术上讲,你是对的,因为这就是“unix 时间”的定义。但是,将本地时间获得的时间戳编码为 UTC (time.mktime(datetime.now().timetuple()) vs time.mktime(datetime.utcnow().timetuple()))当然不是闻所未闻的。当然,严格来说,这些不是 unix 时间 时间戳。我将编辑答案以使其更清楚
  • 不要迷惑人。 OP询问“纪元时间戳”,意思是POSIX时间戳(POSIX时间)。
  • @J.F.Sebastian 您还会注意到 OP 发布了一个示例时间戳,并且似乎自动假定它是 Unix 时间。就个人而言,在假设它们是 Unix 时间之前必须在本地时间解析时间戳,我宁愿有人向我指出这一点,也不愿坚持人们非正式地称为“Unix 时间”的所有内容都在 UTC 中。 IMMV。
【解决方案2】:

将 POSIX 时间戳转换为代表 UTC 时间的 datetime.datetime 对象:

from datetime import datetime, timedelta, timezone

timestamp = 1351036517.179364
utc_time = datetime(1970, 1, 1, tzinfo=timezone.utc) + timedelta(seconds=timestamp)
# -> 2012-10-23 23:55:17.179363+00:00

如果你的 Python 版本不支持datetime.timezone;您可以省略它,以在 UTC 中获取天真的日期时间对象。


我需要 datetime 对象来计算两个数据点之间的时间差,另一个数据点也是一个 datetime 对象。

如果幼稚的 datetime 对象表示具有不同 UTC 偏移量的本地时间,则您无法直接比较它们,否则您可能会得到错误的结果。您要么需要时区感知 datetime 对象,要么应首先将 datetime 对象转换为 UTC。见

【讨论】:

    【解决方案3】:

    TLDR

    使用fromtimestamp 引用in the documentation

    返回与 POSIX 时间戳对应的本地日期 [...如果提供了 tz...] 时间戳将转换为 [提供] tz 的时区。

    给定一个 UNIX/EPOCH 时间戳

    这是一个由 py​​thon 生成的时间戳示例(感谢@jfs 和Paul Ganssle 更新)

    from datetime import datetime, timezone
    epoch = datetime.now(tz=timezone.utc).timestamp()  # example: 1520020585.536527
    

    注意:并非所有纪元都相同,使用 time.time() 会显示自 platform dependent epoch 以来经过的秒数,而 date.timestamp() 会为您提供 what its claims is a POSIX timestamp,请参阅下面的注意事项 em>

    注意:我特别避免将 .timestamp() 的输出称为“符合 POSIX”的时间戳。如果您的应用程序depends on that level of accuracy,那么您可能想要使用.timestamp()以外的其他东西

    注意:使用datetime.now give a higher precision

    注意:我们可以省略上面的 tz 参数,但使用时区感知日期是一个好习惯,因为 python 3 在使用幼稚日期时可能会做出错误的假设(或不要在我们认为会出错的地方抛出错误)

    将时间戳转换为日期时间对象

    给定时间戳(例如 1520020585.536527),我们可以使用 fromtimestamp 将其转换为日期时间 tz 感知对象,如下所示:

    from datetime import datetime, timezone
    ts = 1520020585.536527  # remember me? I'm the epoch example output from above
    utc_date = datetime.fromtimestamp(ts, tz=timezone.utc) # outputs: datetime date object
    

    注意fromtimestamp 需要一个“POSIX”时间戳,我们在这里提供的tz 只是为了避免幼稚的日期时间对象。 fromtimestamp 将为我们提供的时区执行任何需要的转换,但是哪个时区比 UTC 更好,对吧?

    注意:尽管 python 文献明确将输入 fromtimestamp() 引用为“POSIX”时间戳,但并未明确将输入称为“POSIX 兼容”,因此我们只能从其文献的其他部分推断“POSIX”时间戳是什么,例如当它将 POSIX 输出称为“由 time.time() 返回”时

    【讨论】:

    • DT.datetime.utcnow().timestamp()错误的。 .utcnow() 返回一个简单的日期时间对象(没有 tzinfo)。 .timestamp() 将天真的 datetime 对象解释为本地时间(可能具有非零 UTC 偏移量(可能))。要获取当前的“纪元时间戳”,只需调用time.time()。如果你想让.timestamp() 方法工作,那么传递一个时区感知日期时间对象,例如DT.datetime.now(DT.timezone.utc).timestamp()。反过来,从“纪元时间戳”获取时区感知日期时间对象:DT.datetime.fromtimestamp(ts, tz) 其中tz 是所需的时区。
    • @jfs 非常感谢您花时间指出我的错误并给予更正!鉴于我链接到它,我应该仔细阅读文档。我在您的帮助下更新了解决方案。我相信它现在状态良好:D
    • 文本具有误导性:fromtimestamp 参数(“自纪元以来的秒数”)不依赖于生成其 arg 的本地时区。无论您当前的本地时区是什么,time.time() 都会返回相同的值。
    • @jfs 不错,我已经根据您的反馈进行了一些更新,非常感谢!
    • 关键是答案中的代码产生了错误的值(不是它建议它应该产生的值)。运行我在上面提供的示例,亲自查看DT.datetime.now(DT.timezone.utc).timestamp() 在某些情况下不返回 POSIX 时间戳。我没有仔细研究它,但我的猜测是 now(utc)TZ=right/UTC 产生不同的时间,但 .timestamp() 公式对于“正确”时区失败(“正确”时间戳计数闰秒和不同的纪元是使用)repl.it/@zed1/unix-time-in-right-timezone
    猜你喜欢
    • 1970-01-01
    • 2017-07-02
    • 1970-01-01
    • 1970-01-01
    • 2021-01-18
    • 2018-08-03
    • 2020-06-24
    • 1970-01-01
    • 2014-04-28
    相关资源
    最近更新 更多