Иль*_*ков 7 python copy list dataframe pandas
我已经用 pd.Series 和 pd.DataFrame 进行了一段时间的实验,并遇到了一些奇怪的问题。假设我有以下 pd.DataFrame:
df = pd.DataFrame({'col':[[1,2,3]]})
请注意,该数据框包括包含列表的列。我想修改此数据框的副本并返回其修改后的版本,以便初始版本保持不变。为了简单起见,假设我想在其单元格中添加整数“4”。
我尝试过以下代码:
def modify(df):
dfc = df.copy(deep=True)
dfc['col'].iloc[0].append(4)
return dfc
modify(df)
print(df)
Run Code Online (Sandbox Code Playgroud)
问题是,除了新的副本之外dfc,初始的 DataFramedf也被修改了。为什么?我应该怎么做才能防止初始数据帧被修改?我的pandas版本是0.25.0
从这里的文档,在注释部分:
当 deep=True 时,数据会被复制,但实际的 Python 对象不会被递归复制,只会复制对象的引用。这与标准库中的 copy.deepcopy 形成对比,后者递归地复制对象数据(请参见下面的示例)。
在 a 中嵌入可变对象。DataFrame 是一种反模式
所以这个函数正在按照开发人员的预期工作——可变对象(例如列表)不应嵌入到 DataFrame 中。
我找不到copy.deepcopy在 DataFrame 上按预期工作的方法,但我确实使用pickle找到了一个相当糟糕的解决方法:
import pandas as pd
import pickle
df = pd.DataFrame({'col':[[1,2,3]]})
def modify(df):
dfc = pickle.loads(pickle.dumps(df))
print(dfc['col'].iloc[0] is df['col'].iloc[0]) #Check if we've succeeded in deepcopying
dfc['col'].iloc[0].append(4)
print(dfc)
return dfc
modify(df)
print(df)
Run Code Online (Sandbox Code Playgroud)
输出:
False
col
0 [1, 2, 3, 4]
col
0 [1, 2, 3]
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
6165 次 |
| 最近记录: |