我有一组看起来像这样的数据(3列)。日期和时间在1列中,时区在另一列中。
location,time,zone
EASTERN HILLSBOROUGH,1/27/2015 12:00,EST-5
EASTERN HILLSBOROUGH,1/24/2015 7:00,EST-5
EASTERN HILLSBOROUGH,1/27/2015 6:00,EST-5
EASTERN HILLSBOROUGH,2/14/2015 8:00,EST-5
EASTERN HILLSBOROUGH,2/7/2015 22:00,EST-5
EASTERN HILLSBOROUGH,2/2/2015 2:00,EST-5
我正在使用pandas
来解析日期和时间及其各自的时区。在read_csv
我可以parse_dates = [[1,2]]
根据docs将列合并为1并解析它们。{/ p>
所以现在新数据看起来像这样(2列)
location,time_zone
EASTERN HILLSBOROUGH,1/27/2015 12:00 EST-5
EASTERN HILLSBOROUGH,1/24/2015 7:00 EST-5
EASTERN HILLSBOROUGH,1/27/2015 6:00 EST-5
EASTERN HILLSBOROUGH,2/14/2015 8:00 EST-5
EASTERN HILLSBOROUGH,2/7/2015 22:00 EST-5
EASTERN HILLSBOROUGH,2/2/2015 2:00 EST-5
但是,如果我输入df['time_zone'].dtype
,我的dtype('O')
不是datetimelike
,因为我无法使用dt
访问者。
我还能如何正确解析这两列?
答案 0 :(得分:0)
不确定这是否是你想要的,但你可以直接读入(没有任何日期时间解析)然后使用to_datetime(注意新变量time_zone比时间晚5小时)。
df['time_zone'] = pd.to_datetime( df.time + df.zone )
location time zone time_zone
0 EASTERN HILLSBOROUGH 1/27/2015 12:00 EST-5 2015-01-27 17:00:00
1 EASTERN HILLSBOROUGH 1/24/2015 7:00 EST-5 2015-01-24 12:00:00
2 EASTERN HILLSBOROUGH 1/27/2015 6:00 EST-5 2015-01-27 11:00:00
3 EASTERN HILLSBOROUGH 2/14/2015 8:00 EST-5 2015-02-14 13:00:00
4 EASTERN HILLSBOROUGH 2/7/2015 22:00 EST-5 2015-02-08 03:00:00
5 EASTERN HILLSBOROUGH 2/2/2015 2:00 EST-5 2015-02-02 07:00:00
df.info()
location 6 non-null object
time 6 non-null object
zone 6 non-null object
time_zone 6 non-null datetime64[ns]
答案 1 :(得分:0)
根据pytz module:
处理时间的首选方法是始终使用UTC, 仅在生成要读取的输出时转换为本地时间 人类。
我不相信你的时区是标准的,这使转换变得有点棘手。但是,我们应该能够剥离时区偏移并使用datetime.timedelta
将其添加到UTC时间。这是一个黑客,我希望我知道一个更好的方法。
我认为所有时间都记录在当地时区,所以1/27/2015 12:00 EST-5将是2015年1月27日17:00 UTC。
from pytz import utc
import datetime as dt
df = pd.read_csv('times.csv')
df['UTC_time'] = [utc.localize(t) - dt.timedelta(hours=int(h))
for t, h in zip(pd.to_datetime(df.time),
df.zone.str.extract(r'(-?\d+)'))]
>>> df
location time zone UTC_time
0 EASTERN HILLSBOROUGH 1/27/2015 12:00 EST-5 2015-01-27 17:00:00+00:00
1 EASTERN HILLSBOROUGH 1/24/2015 7:00 EST-5 2015-01-24 12:00:00+00:00
2 EASTERN HILLSBOROUGH 1/27/2015 6:00 EST-5 2015-01-27 11:00:00+00:00
3 EASTERN HILLSBOROUGH 2/14/2015 8:00 EST-5 2015-02-14 13:00:00+00:00
4 EASTERN HILLSBOROUGH 2/7/2015 22:00 EST-5 2015-02-08 03:00:00+00:00
5 EASTERN HILLSBOROUGH 2/2/2015 2:00 EST-5 2015-02-02 07:00:00+00:00
检查单个时间戳,您会注意到时区设置为UTC:
>>> df.UTC_time.iat[0]
Timestamp('2015-01-27 17:00:00+0000', tz='UTC')
>>> df.UTC_time.iat[0].tzname()
'UTC'
要在不同的时区显示它们:
fmt = '%Y-%m-%d %H:%M:%S %Z%z'
>>> [t.astimezone('EST').strftime(fmt) for t in df.UTC_time]
['2015-01-27 12:00:00 EST-0500',
'2015-01-24 07:00:00 EST-0500',
'2015-01-27 06:00:00 EST-0500',
'2015-02-14 08:00:00 EST-0500',
'2015-02-07 22:00:00 EST-0500',
'2015-02-02 02:00:00 EST-0500']
这是一个测试。让我们改变df
中的时区,看看替代解决方案是否仍然有效:
df['zone'] = ['EST-5', 'CST-6', 'MST-7', 'GST10', 'PST-8', 'AKST-9']
df['UTC_time'] = [utc.localize(t) - dt.timedelta(hours=int(h))
for t, h in zip(pd.to_datetime(df.time),
df.zone.str.extract(r'(-?\d+)'))]
>>> df
location time zone UTC_time
0 EASTERN HILLSBOROUGH 1/27/2015 12:00 EST-5 2015-01-27 17:00:00+00:00
1 EASTERN HILLSBOROUGH 1/24/2015 7:00 CST-6 2015-01-24 13:00:00+00:00
2 EASTERN HILLSBOROUGH 1/27/2015 6:00 MST-7 2015-01-27 13:00:00+00:00
3 EASTERN HILLSBOROUGH 2/14/2015 8:00 GST10 2015-02-13 22:00:00+00:00
4 EASTERN HILLSBOROUGH 2/7/2015 22:00 PST-8 2015-02-08 06:00:00+00:00
5 EASTERN HILLSBOROUGH 2/2/2015 2:00 AKST-9 2015-02-02 11:00:00+00:00
查看python docs以了解有关使用时间的更多详细信息。
这是一篇关于这个主题的好文章。 How to make an unaware datetime timezone aware in python
这里是tz数据库时区的link。