Python 2.x中datetime列相减触发TypeError问题排查求助
看起来你遇到的问题有点棘手——明明df.dtypes显示两列都转成了datetime64[ns],但减法操作还是提示其中一列是object类型。结合你使用Python 2.x的情况,我梳理了几个可能的原因和对应的解决办法:
1. 检查转换是否真正覆盖所有行
有时候pd.to_datetime会让列的整体dtype显示为datetime64[ns],但个别格式错误的字符串行可能没被成功转换,仍然保留为object类型,导致列内部存在混合类型。
你可以用以下代码检查每列的元素实际类型:
print("Time列元素类型:", df['time'].apply(type).unique()) print("EVS_START列元素类型:", df['EVS_START'].apply(type).unique())
如果输出里包含<type 'str'>,说明确实有未转换成功的字符串。这时候可以在转换时加上errors='raise'强制抛出错误,定位到有问题的行:
df['time'] = pd.to_datetime(df['time'], errors='raise') df['EVS_START'] = pd.to_datetime(df['EVS_START'], errors='raise')
找到无效值后,要么修正数据格式,要么用errors='coerce'把无效值转为NaT(这样元素类型会统一为datetime)。
2. 确认赋值操作真正生效
在Python 2.x的旧版pandas中,如果你的df是从另一个DataFrame切片得到的(比如df = original_df[['time', 'EVS_START']]),直接赋值可能不会修改原数据(因为切片可能是视图而非副本)。这时候需要用loc确保赋值生效:
df.loc[:, 'time'] = pd.to_datetime(df['time']) df.loc[:, 'EVS_START'] = pd.to_datetime(df['EVS_START'])
3. 检查pandas版本是否过旧
Python 2.x对应的pandas版本普遍偏老(比如0.20之前的版本),这类旧版本可能存在datetime类型处理的bug。你可以先查看当前pandas版本:
print(pd.__version__)
如果版本低于0.20,建议升级到Python 2.x支持的最高pandas版本(比如0.24.2,这是最后一个支持Python 2.x的版本),很多类型相关的bug在新版本中已经修复。
4. 排除列名拼写错误
虽然听起来基础,但有时候可能不小心拼错了列名——比如转换的是EVS_Start(首字母小写),但计算时用的是EVS_START,导致实际调用的还是未转换的原列。你可以用df.columns确认列名是否完全一致。
尝试完这些步骤后,再执行时间差计算,应该就能解决问题了。
内容的提问来源于stack exchange,提问作者Christian

