Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
439 views
in Technique[技术] by (71.8m points)

python - Try using .loc[row_indexer,col_indexer] = value instead warning even after using the formal

This is one of the lines in my code where I get the SettingWithCopyWarning:

value1['Total Population']=value1['Total Population'].replace(to_replace='*', value=4)

Which I then changed to :

row_index= value1['Total Population']=='*'
value1.loc[row_index,'Total Population'] = 4

This still gives the same warning. How do I get rid of it?

Also, I get the same warning for a convert_objects(convert_numeric=True) function that I've used, is there any way to avoid that.

 value1['Total Population'] = value1['Total Population'].astype(str).convert_objects(convert_numeric=True)

This is the warning megsage that I get:

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

See the the caveats in the documentation: http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-view-versus-copy

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

If you use .loc[row,column] and still get the same error, it's probably because of copying another data frame. You have to use .copy().

This is a step by step error reproduction:

import pandas as pd

d = {'col1': [1, 2, 3, 4], 'col2': [3, 4, 5, 6]}
df = pd.DataFrame(data=d)
df
#   col1    col2
#0  1   3
#1  2   4
#2  3   5
#3  4   6

Creating a new column and updating its value:

df['new_column'] = None
df.loc[0, 'new_column'] = 100
df
#   col1    col2    new_column
#0  1   3   100
#1  2   4   None
#2  3   5   None
#3  4   6   None

No error I receive. However, let's create another data frame given the previous one:

new_df = df.loc[df.col1>2]
new_df
#col1   col2    new_column
#2  3   5   None
#3  4   6   None

Now, using .loc, I will try to replace some values in the same manner:

new_df.loc[2, 'new_column'] = 100

However, I got this hateful warning again:

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

See the caveats in the documentation: https://pandas.pydata.org/pandas-docs/stable/user_guide/indexing.html#returning-a-view-versus-a-copy

SOLUTION

use .copy() while creating the new data frame will solve the warning:

new_df = df.loc[df.col1>2].copy()
new_df.loc[2, 'new_column'] = 100

Now, you won't receive any warnings!

If your data frame is created using a filter on top of another data frame, always use .copy().


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...