python - 使用 iloc 或 loc 将多列转换为日期时间
问题描述
我不确定这是否是预期的行为,但下面是一个示例数据框。
df = pd.DataFrame([['2020-01-01','2020-06-30','A'],
['2020-07-01','2020-12-31','B']],
columns = ['start_date', 'end_date', 'field1'])
在升级到 pandas 版本之前1.3.4
,我相信我能够像这样转换列 dtypes:
df.iloc[:,0:2] = df.iloc[:,0:2].apply(pd.to_datetime)
尽管似乎已将列转换为日期时间,
start_date end_date field1
0 2020-01-01 00:00:00 2020-06-30 00:00:00 A
1 2020-07-01 00:00:00 2020-12-31 00:00:00 B
dtypes 似乎仍然是对象:
start_date object
end_date object
field1 object
我知道我可以使用下面的代码做同样的事情,我只是想知道这是否是loc
and的预期行为iloc
。
df[['start_date', 'end_date']] = df[['start_date', 'end_date']].apply(pd.to_datetime)
start_date datetime64[ns]
end_date datetime64[ns]
field1 object
解决方案
此行为是1.3.0中引入的更改的一部分。
loc
当使用or设置整列时iloc
,pandas 将尝试将值插入现有数据中,而不是创建一个全新的数组。
这意味着如果新数组可以适合现有类型,iloc
并且loc
将尝试不更改数组的 dtype :
import pandas as pd
df = pd.DataFrame({'A': [1.2, 2.3], 'B': [3.4, 4.5]})
print(df)
print(df.dtypes)
df.loc[:, 'A':'B'] = pd.DataFrame({'A': [1, 2], 'B': [3, 4]})
print(df)
print(df.dtypes)
输出:
A B
0 1.2 3.4
1 2.3 4.5
A float64
B float64
dtype: object
A B
0 1.0 3.0
1 2.0 4.0
A float64
B float64
dtype: object
相反:
设置时切勿原位操作frame[keys] = values
:
当使用新数组设置多个列时,
frame[keys] = values
将替换这些键的预先存在的数组,这些数组不会被覆盖(GH39510)。结果,列将保留值的 dtype,从不转换为现有数组的 dtype。
import pandas as pd
df = pd.DataFrame({'A': [1.2, 2.3], 'B': [3.4, 4.5]})
print(df)
print(df.dtypes)
df[['A', 'B']] = pd.DataFrame({'A': [1, 2], 'B': [3, 4]})
print(df)
print(df.dtypes)
输出:
A B
0 1.2 3.4
1 2.3 4.5
A float64
B float64
dtype: object
A B
0 1 3
1 2 4
A int64
B int64
dtype: object
考虑到这些变化,我们现在必须执行以下操作:
import pandas as pd
df = pd.DataFrame([['2020-01-01', '2020-06-30', 'A'],
['2020-07-01', '2020-12-31', 'B']],
columns=['start_date', 'end_date', 'field1'])
cols = df.columns[0:2]
df[cols] = df[cols].apply(pd.to_datetime)
# or
# df[df.columns[0:2]] = df.iloc[:, 0:2].apply(pd.to_datetime)
print(df)
print(df.dtypes)
输出:
start_date end_date field1
0 2020-01-01 2020-06-30 A
1 2020-07-01 2020-12-31 B
start_date datetime64[ns]
end_date datetime64[ns]
field1 object
dtype: object
推荐阅读
- python - 在 Python 中将字符串添加到列表中
- postgresql - 从 postgresql DB 中选择多条记录并使用 WSO2ESB 插入到另一个表中
- websocket - 如何将 mpsc Receiver 分配给线程?
- swagger - OAS3:为什么在响应中定义 Accept 标头?
- apache-spark - 在 IntelliJ 上运行的异常 Spark sql 代码,即 java.lang.IllegalArgumentException:
- python - 如何递归地在python中查找目录
- c - C管道来自父进程的错误值
- google-apps-script - 从 Gmail 插件添加密件抄送地址
- angular - Angular Universal Microsoft Edge 和文档注入问题
- php - 带有引号的MYSQL查询对象