所以我有一个数据集(一堆csv文件),它包含以下形式的(匿名)日期时间:
3202-11-11 14:51:00 EST
每个实体的日期已经移动了一些随机时间。因此,给定实体的时间差异仍然有意义。
尝试使用例如转换时
pd.to_datetime(['3202-11-11 14:51:00 EST'], format='%Y-%m-%d %H:%M:%S EST')
,这将导致“OutOfBoundsDatetime”错误。
对于我的用例,理想的是指定在读取csv文件时转移所有日期的年数,s.t。它们在有效的pandas日期时间范围内。
您是否知道如何有效地解决这个问题?我必须在~40k实体/ csv文件上执行此操作,每个csv有10到10k个这样的日期。 (我的非效率想法:通过python datetime,它可以工作多年,直到9999,在那里转换日期,然后转换为pandas datetime)
编辑:我也在IRC #pydata中提出了这个问题并得到了这个答案(谢谢jboy):
>>> from datetime import timedelta
>>> offset = timedelta(days=10000)
>>> df
time
0 3001-01-01 01:00:01
1 3001-01-01 01:00:02
2 3001-01-01 01:00:05
3 3001-01-01 01:00:09
>>> df['time'].map(lambda t: t - offset)
0 2973-08-15 01:00:01
1 2973-08-15 01:00:02
2 2973-08-15 01:00:05
3 2973-08-15 01:00:09
Name: time, dtype: object
我唯一要做的就是:
df['time'].map(lambda t: datetime.datetime.strptime(t, '%Y-%m-%d %H:%M:%S EST')-offset)
因为我的时间栏仍然是str而不是datetime.datetime。
答案 0 :(得分:0)
你可以做的一件事就是在字符串级别处理这个问题,扣除一些年份(在下面,1200):
s = '3202-11-11 14:51:00 EST'
>>> In [21]: pd.to_datetime(str(int(s[: 4]) - 1200) + s[4: ])
Out[21]: Timestamp('2002-11-11 14:51:00')
您也可以对此进行矢量化。假设你从
开始dates = pd.Series([s, s])
然后你可以使用
>>> pd.to_datetime((dates.str[: 4].astype(int) - 1200).astype(str) + dates.str[4: ])
0 2002-11-11 14:51:00
1 2002-11-11 14:51:00
dtype: datetime64[ns]
答案 1 :(得分:0)
pandas datetime对象使用64位整数来表示时间,由于它具有纳秒级分辨率,因此上限位于2262-04-11
,引用为here。
我不确定你是否计划对时间对象进行任何时间操作,但如果你只是想在数据框中表示它们,我就不明白为什么不使用python datetime对象只是按原样表示它们而不做任何时间转换:
示例强>
from datetime import datetime
s = pd.Series(['3202-11-11 14:51:00 EST', '9999-12-31 12:21:00 EST'])
s = s.apply(lambda x: datetime.strptime(x[:-4], "%Y-%m-%d %H:%M:%S"))
<强>返回强>
0 3202-11-11 14:51:00
1 9999-12-31 12:21:00
dtype: object
在第一个单元格上运行快速嗅探类型检查:
>>> type(s[0])
<type 'datetime.datetime'>