Python 和 MATLAB 在根据日期时间计算 POSIX 方面存在分歧
Disagreement between Python and MATLAB in calculating POSIX from datetime
在 MATLAB 中,我可以轻松地将日期时间对象转换为 posix:
start_time = datetime('2020-04-30 10:05:00');
start_time_unix = posixtime(start_time)
哪个returns:
start_time_unix = 1.588241100000000e+09.
在 Python 中,我创建了一个类似的日期时间对象并尝试将其转换为 posix:
import time
import datetime
import numpy as np
time_string = '2020-04-30 10:05:00'
calendar, clock = time_string.split(' ')
year,month,day = [np.int(x) for x in calendar.split('-')]
hour,minute,second = [np.int(x) for x in clock.split(':')]
dt = datetime.datetime(year, month, day, hour, minute, second)
ut = time.mktime(dt.timetuple())
此时,
ut = 1588262700.0
如果小时和分钟混淆,
dt2 = datetime.datetime(year, month, day, minute, hour, second)
ut2 = time.mktime(dt2.timetuple())
returns
ut2 = 1588245000.0
为什么我看到 MATLAB 和 Python 之间存在这种差异?另外,有没有办法更有效地解析 date/time 字符串并将其转换为 posix?
在 Python 中,如果您将不包含时区信息或 UTC 偏移量的 date/time 字符串解析为 datetime
对象,则生成的对象是原始对象,即它不了解任何时区、DST 或 UTC 偏移量。
来自the docs:
A naive object does not contain enough information to unambiguously
locate itself relative to other date/time objects. Whether a naive
object represents Coordinated Universal Time (UTC), local time, or
time in some other timezone is purely up to the program, just like it
is up to the program whether a particular number represents metres,
miles, or mass. Naive objects are easy to understand and to work with,
at the cost of ignoring some aspects of reality.
Python 将默认假定一个天真的 datetime
对象属于您操作系统的时区!
来自the docs的更多内容:
Warning: Because naive datetime objects are treated by many datetime methods as local times, it is preferred to use aware
datetimes to represent times in UTC.
对于给定的示例,您需要指定时区信息以避免歧义:
from datetime import datetime, timezone
# parse to datetime, in this case we don't need strptime since string is ISO8601 compatible
dtobj = datetime.fromisoformat('2020-04-30 10:05:00')
# naive, no tz info: datetime.datetime(2020, 4, 30, 10, 5)
# add a timezone, for UTC, we can use timezone.utc from the datetime module:
dtobj = dtobj.replace(tzinfo=timezone.utc)
# tz-aware: datetime.datetime(2020, 4, 30, 10, 5, tzinfo=datetime.timezone.utc)
# now we can obtain the posix timestamp:
posix = dtobj.timestamp()
print(posix)
# 1588241100.0
如果您打算经常使用 Python 中的时间序列数据,请查看 dateutil 包。
在 MATLAB 中,我可以轻松地将日期时间对象转换为 posix:
start_time = datetime('2020-04-30 10:05:00');
start_time_unix = posixtime(start_time)
哪个returns:
start_time_unix = 1.588241100000000e+09.
在 Python 中,我创建了一个类似的日期时间对象并尝试将其转换为 posix:
import time
import datetime
import numpy as np
time_string = '2020-04-30 10:05:00'
calendar, clock = time_string.split(' ')
year,month,day = [np.int(x) for x in calendar.split('-')]
hour,minute,second = [np.int(x) for x in clock.split(':')]
dt = datetime.datetime(year, month, day, hour, minute, second)
ut = time.mktime(dt.timetuple())
此时,
ut = 1588262700.0
如果小时和分钟混淆,
dt2 = datetime.datetime(year, month, day, minute, hour, second)
ut2 = time.mktime(dt2.timetuple())
returns
ut2 = 1588245000.0
为什么我看到 MATLAB 和 Python 之间存在这种差异?另外,有没有办法更有效地解析 date/time 字符串并将其转换为 posix?
在 Python 中,如果您将不包含时区信息或 UTC 偏移量的 date/time 字符串解析为 datetime
对象,则生成的对象是原始对象,即它不了解任何时区、DST 或 UTC 偏移量。
来自the docs:
A naive object does not contain enough information to unambiguously locate itself relative to other date/time objects. Whether a naive object represents Coordinated Universal Time (UTC), local time, or time in some other timezone is purely up to the program, just like it is up to the program whether a particular number represents metres, miles, or mass. Naive objects are easy to understand and to work with, at the cost of ignoring some aspects of reality.
Python 将默认假定一个天真的 datetime
对象属于您操作系统的时区!
来自the docs的更多内容:
Warning: Because naive datetime objects are treated by many datetime methods as local times, it is preferred to use aware datetimes to represent times in UTC.
对于给定的示例,您需要指定时区信息以避免歧义:
from datetime import datetime, timezone
# parse to datetime, in this case we don't need strptime since string is ISO8601 compatible
dtobj = datetime.fromisoformat('2020-04-30 10:05:00')
# naive, no tz info: datetime.datetime(2020, 4, 30, 10, 5)
# add a timezone, for UTC, we can use timezone.utc from the datetime module:
dtobj = dtobj.replace(tzinfo=timezone.utc)
# tz-aware: datetime.datetime(2020, 4, 30, 10, 5, tzinfo=datetime.timezone.utc)
# now we can obtain the posix timestamp:
posix = dtobj.timestamp()
print(posix)
# 1588241100.0
如果您打算经常使用 Python 中的时间序列数据,请查看 dateutil 包。