首页 > 解决方案 > 添加新的熊猫系列并设置为 false

问题描述

我正在添加以下代码:

 r = df_1[~df_1isin(
        df_2.to_dict('list')).all(1)] 
 r['is_sent'] = pd.Series(False).bool()

目的是缩小两个数据框之间的搜索范围,然后我想添加一个新列(pd.series)并将这些发现设置为 false。这做了我打算做的,但返回了一条消息:

“试图在 DataFrame 的切片副本上设置一个值。尝试改用 .loc[row_indexer,col_indexer] = value”

谁能解释这个引用的内容并举例说明正确的方法是什么?

标签: python-3.xpandasdataframeseries

解决方案


这个问题是切片 DataFrame 会weakref在切片和原始 DataFrame 之间创建一个。然后,当您进行分配时,这会触发下一行的警告。

import pandas as pd

df = pd.DataFrame([0,1,1,1,2])
r = df[df.isin([1]).all(1)]

r['new_col'] = False
#<ipython-input-210-d5f9bda478c4>:9: SettingWithCopyWarning:  ...

您可以使用内置方法验证是否存在弱引用._is_copy

df = pd.DataFrame([0,1,1,1,2])
r = df[df.isin([1]).all(1)]
r._is_copy
#<weakref at 0x142b10e00; to 'DataFrame' at 0x14361ed00>

打破这个最简单的方法是使用.copy()强制深层复制,以便与r没有关系df,这将消除警告。

r = df[df.isin([1]).all(1)].copy()
r._is_copy
#None

r['new_col'] = False
# No warning!

最后,这个警告似乎经常被击中或错过,但这是因为许多 pandas 操作返回一个新对象,因此如果在切片和赋值之间存在操作,则这些操作本身很可能会破坏弱引用,从而阻止警告。例如,像乘以 2 这样的简单操作会创建一个新对象,而您不会收到任何警告。

df = pd.DataFrame([0,1,1,1,2])

r = df[df.isin([1]).all(1)]
print(r._is_copy)
#<weakref at 0x13e6ad0e0; to 'DataFrame' at 0x1436227c0>

r = r*2   # Breaks the reference
print(r._is_copy)
# None

r['new_col'] = False
# No warning!

推荐阅读