将 Python DateTime 字符串转换为整数毫秒

Conversion of Python DateTime string into integer milliseconds

我想将 UTC TimeDate 时间戳字符串转换成毫秒的整数值(可能需要是 64 位数量),这样当存储在 mySQL 数据库列。这个 UTC 字符串是从另一个库生成的,我将它存储为一种每用户 GUID。

datetime 或 dateutil 能否将其转换为单个整数值(如 "milliseconds since epoch")?还是我需要自己做?

使用这种方法解析:

myDateTime = dateutil.parser.parse("2015-06-27T02:10:05.653000Z")
print("Parsed datetime String is {0}, ordinal value is {1}".format(myDateTime, myDateTime.toordinal()))

给出输出:

Parsed datetime String is 2015-06-27 02:10:05.652999+00:00, ordinal value is 735776

…只给出日期的序数值。此外,如果我有一个整数 653 毫秒的时间,那么我希望被解析的对象知道它有 653 毫秒,而不是 652999。

Scott 和 GordonLinoff 都为解决我的问题提供了极好的帮助。我正在添加完整性的答案。

Python 将 UTC 日期时间字符串转换为自纪元以来的毫秒数的代码:

编辑以消除 strftime:

from datetime import datetime

def convert_UTC_zulu_string_to_milliseconds_since_epoch(myUTCzuluString):
    try:
        dt_unix = datetime.strptime(myUTCzuluString, "%Y-%m-%dT%H:%M:%S.%fZ")
        epoch = datetime.utcfromtimestamp(0)
        delta = dt_unix - epoch
        millisecondsSinceEpoch = long(delta.total_seconds() * 1000)

    except:
        millisecondsSinceEpoch = 0L

    return millisecondsSinceEpoch


myUTCzuluString = "2015-06-27T02:10:05.653000Z"
millisecondsSinceEpoch = convert_UTC_zulu_string_to_milliseconds_since_epoch(myUTCzuluString)
print("Milliseconds since epoch: {0}".format(millisecondsSinceEpoch))

另外:如果我将列定义为 DATETIME(6) 数据类型,mysql 将直接从字符串中接受带有 milliseconds/microseconds 的日期时间值:

UPDATE myTable SET myDateTimeField = '2015-06-27T02:10:05.653000Z'

请注意,在 UTC 日期时间字符串末尾包含 "Z" 会导致来自 mysql 的截断警告。

我无法确定 DATETIME(6) 比 DATETIME 增加的精度是否导致 mysql 的 InnoDB 引擎使用超过 8 个字节,这是我研究这个问题的最初原因之一。

[根据评论中的建议进行编辑]

使用Ben Alpert's answer to How can I convert a datetime object to milliseconds since epoch (unix time) in Python我们可以做以下事情:

from datetime import datetime
def unix_time(dt):
    epoch = datetime.utcfromtimestamp(0)
    delta = dt - epoch
    return delta.total_seconds()

def unix_time_millis(dt):
    return int(unix_time(dt) * 1000)

a = datetime.strptime("2015-06-27T02:10:05.653000Z", "%Y-%m-%dT%H:%M:%S.%fZ")
unix_time_millis(a)

returns:

1435371005653

相当于:2015 年 6 月 27 日星期六 02:10:05 GMT(如预期)

我们还可以使用 datetime 的 .strftime('%s') 来获取 unix 时间,甚至毫秒使用以下内容(但不建议这样做):

from decimal import Decimal

int(Decimal(datetime.strptime("2015-06-27T02:10:05.653000Z", "%Y-%m-%dT%H:%M:%S.%fZ").strftime('%s.%f'))*1000)

returns:

1435396205653

相当于:2015 年 6 月 27 日星期六 09:10:05 GMT(我在圣地亚哥的 mac;注意:这比我们预期的少了 7 个小时)。

错误原因由J.F描述。塞巴斯蒂安在上面 link 的评论和 this 中关于 .strftime('%s') 行为的回答。 J.F。塞巴斯蒂安指出 "it is not supported, it is not portable, it may silently produce a wrong result for an aware datetime object, it fails if input is in UTC (as in the question) but local timezone is not UTC"

分为两部分:

  • "2015-06-27T02:10:05.653000Z"转换为日期时间对象,参见How to parse ISO formatted date in Python?

    import re
    from datetime import datetime
    
    utc_time = datetime(*map(int, re.findall(r'\d+', time_string))
    
  • 将 UTC 时间转换为 POSIX 时间戳整数毫秒,参见 How can I convert a datetime object to milliseconds since epoch (unix time) in Python?

    from datetime import datetime
    
    def timestamp_millis(utc_time, epoch=datetime(1970, 1, 1)):
        td = utc_time - epoch
        return (td.microseconds + (td.seconds + td.days * 86400) * 10**6) // 10**3