防止SettingWithCopy警告,正确使用Pandas数据帧的视图/副本



在更改从另一个数据帧的切片创建的数据帧时,是否应该始终使用.copy()方法显式生成副本?否则,我将收到SettingWithCopy警告。然而,在这种情况下,它并没有导致任何麻烦;原始数据帧保持不变。

>>> import pandas as pd
>>> df = pd.DataFrame([[6,3,2],[4,3,2],[5,4,2],[4,3,5]], columns=['a', 'b', 'c'])
>>> df
a  b  c
0  6  3  2
1  4  3  2
2  5  4  2
3  4  3  5
>>> df2 = df.loc[df.a<6, :]
>>> df2.loc[df2.b==3, 'b'] = 99
/usr/lib/python3/dist-packages/pandas/core/indexing.py:117: SettingWithCopyWarning: 
A value is trying to be set on a copy of a slice from a DataFrame
See the caveats in the documentation: http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-view-versus-copy
self._setitem_with_indexer(indexer, value)
__main__:1: SettingWithCopyWarning: 
A value is trying to be set on a copy of a slice from a DataFrame
See the caveats in the documentation: http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-view-versus-copy
>>> df
a  b  c
0  6  3  2
1  4  3  2
2  5  4  2
3  4  3  5
>>> df2
a   b  c
1  4  99  2
2  5   4  2
3  4  99  5

或者,如果我执行以下操作,则不会收到任何警告。

>>> df2 = df.loc[df.a<6, :].copy()
>>> df2.loc[df2.b==3, 'b'] = 99
>>> df2
a   b  c
1  4  99  2
2  5   4  2
3  4  99  5
>>> df
a  b  c
0  6  3  2
1  4  3  2
2  5  4  2
3  4  3  5

后者更好吗?(因此我没有得到任何警告)。在什么意义上?是因为我确信df2是一个副本,因此不能更改原始数据帧df吗?

如果用户对命令的解释存在歧义,则会出现SettingWithCopyWarning。在第一种情况下,Panda很清楚应该将值分配给df2。但是,尚不清楚用户是否期望值分配传播到df本身,这就是引发警告的原因。在内部,panda使用数据帧的_is_copy属性对此进行跟踪。创建df2时,_is_copy属性存储对df的弱引用。

In [1]: import pandas as pd
In [2]: df = pd.DataFrame([[6,3,2],[4,3,2],[5,4,2],[4,3,5]], columns=['a', 'b', 'c'])
In [3]: df2 = df.loc[df.a<6, :]
In [4]: df2._is_copy
Out[4]: <weakref at 0x7f0dae5a3770; to 'DataFrame' at 0x7f0daef08850>

在第二种情况下,df2被显式创建为df的副本,因此panda不会将weakref存储到df

In [5]: df2 = df.loc[df.a<6, :].copy()
In [6]: df2._is_copy
In [7]: print(df2._is_copy)
None

df2所做的任何操作都不会影响其他数据帧,因此在值分配中不存在歧义,因此不需要引发SettingWithCopyWarning。

来源:

  • 熊猫文档:http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-查看与复制
  • https://tnwei.github.io/posts/settings-with-copy-warning-pandas/

相关内容

  • 没有找到相关文章

最新更新