当我尝试覆盖特定列(Series对象)时,我收到以下代码的错误:
mask = bond["Actor"] == "Sean Connery"
bond[mask]["Actor"] = "Sir Sean Connery"
但是当我向下移动一个级别而不是编辑这些行的所有列(完整的DataFrame)时,我成功了
mask = bond["Actor"] == "Sean Connery"
bond[mask] = "Sir Sean Connery"
为什么会这样?在第一种情况下,我认为编辑副本并因此错误是不合逻辑的。但同样适用于后一种情况,因为第二个示例也应该返回原始DataFrame的副本。
答案 0 :(得分:0)
您需要loc
才能避免chained indexing:
bond = pd.DataFrame({'Actor':list('abcaef'),
'A':list('efghij'),
'B':list('aaabbb')})
print (bond)
A Actor B
0 e a a
1 f b a
2 g c a
3 h a b
4 i e b
5 j f b
mask = bond["Actor"] == "a"
bond.loc[mask] = "AAA"
#for select all columns :, for columns can be omitted
#bond.loc[mask,:] = "AAA"
print (bond)
A Actor B
0 AAA AAA AAA
1 f b a
2 g c a
3 AAA AAA AAA
4 i e b
5 j f b
#one column Actor
bond.loc[mask, "Actor"] = "AAA"
print (bond)
A Actor B
0 e AAA a
1 f b a
2 g c a
3 h AAA b
4 i e b
5 j f b
答案 1 :(得分:0)
考虑以下单列DataFrame:
export class AppComponent {
inboundClick = false;
}
这是你想要用于切片的面具:
df = pd.DataFrame({'Actor': ['Sean Connery', 'Sean Connery',
'Sean Something', 'Sean Something Else']})
df
Out:
Actor
0 Sean Connery
1 Sean Connery
2 Sean Something
3 Sean Something Else
现在,如果我使用mask = df['Actor'] == 'Sean Connery'
,则会执行此操作:
df[mask]['Actor'] = 'Sir Sean Connery'
df.__getitem__(mask).__setitem__('Actor', 'Sir Sean Connery')
请参阅文档中的警告:http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-view-versus-copy
对于这种情况,它不会修改原始DataFrame:
__main__:1: SettingWithCopyWarning:
A value is trying to be set on a copy of a slice from a DataFrame.
Try using .loc[row_indexer,col_indexer] = value instead
Id 确实修改了一个DataFrame - 这是由df
Out:
Actor
0 Sean Connery
1 Sean Connery
2 Sean Something
3 Sean Something Else
方法返回的,但由于它没有分配给任何东西,所以它会丢失。
相反,在您的第二个示例(__getitem__
)中,执行的代码是:
df[mask] = 'Sir Sean Connery'
由于掩码,您可能认为它也使用df.__setitem__(mask, 'Sir Sean Connery')
,但事实并非如此。它直接使用__getitem__
并将掩码传递给该DataFrame。并且pandas确保我们使用__setitem__
我们可以确保它将在视图上运行。对于__setitem__
的情况,它表示它可以是复制品,也可以是一种观点 - 很难知道。
现在您将看到原始df已被修改:
__getitem__
虽然有一个问题。它起作用,因为我们只有一列。如果我们有另一个专栏,比如说“年”,它会将相应的“年”值设置为“肖恩·康纳利爵士”#39;太。为了避免这种情况,我们使用df
Out:
Actor
0 Sir Sean Connery
1 Sir Sean Connery
2 Sean Something
3 Sean Something Else
作为jezrael指出。它还调用.loc
方法,并允许指定哪些列将更改。
__setitem__
因此,基于掩码和列名设置的最佳做法是使用df = pd.DataFrame({'Actor': ['Sean Connery', 'Sean Connery',
'Sean Something', 'Sean Something Else'],
'Year': [1990, 1990, 1990, 1990]})
df.loc.__setitem__((mask, 'Actor'), 'Sir Sean Connery')
df
Out:
Actor Year
0 Sir Sean Connery 1990
1 Sir Sean Connery 1990
2 Sean Something 1990
3 Sean Something Else 1990
:
.loc
通过这种方式,如果您正在操作副本,则不必担心。