通过 Pandas 中的函数替换 NaN 时索引超出范围
Index out of bounds when replacing NaNs through a function in Pandas
我创建了一个函数,用相应列的方法替换 Pandas 数据框中的 NaN。我用一个小的数据框测试了这个函数,它起作用了。当我将它应用于更大的数据框(30,000 行,9 列)时,我收到错误消息:IndexError: index out of bounds
函数如下:
# The 'update' function will replace all the NaNs in a dataframe with the mean of the respective columns
def update(df): # the function takes one argument, the dataframe that will be updated
ncol = df.shape[1] # number of columns in the dataframe
for i in range(0 , ncol): # loops over all the columns
df.iloc[:,i][df.isnull().iloc[:, i]]=df.mean()[i] # subsets the df using the isnull() method, extracting the positions
# in each column where the
return(df)
我用来测试功能的小数据框如下:
0 1 2 3
0 NaN NaN 3 4
1 NaN NaN 7 8
2 9.0 10.0 11 12
你能解释一下这个错误吗?我们将不胜感激您的建议。
我会使用DataFrame.fillna() method in conjunction with DataFrame.mean()方法:
In [130]: df.fillna(df.mean())
Out[130]:
0 1 2 3
0 9.0 10.0 3 4
1 9.0 10.0 7 8
2 9.0 10.0 11 12
平均值:
In [138]: df.mean()
Out[138]:
0 9.0
1 10.0
2 7.0
3 8.0
dtype: float64
你得到 "index out of bounds" 的原因是因为当 i
是应该是序数位置的迭代时,你正在分配值 df.mean()[i]
。 df.mean()
是一个 Series
,其索引是 df
的列。 df.mean()[something]
表示 something
最好是列名。但它们不是,这就是为什么您会收到错误消息的原因。
您的代码...已修复
def update(df): # the function takes one argument, the dataframe that will be updated
ncol = df.shape[1] # number of columns in the dataframe
for i in range(0 , ncol): # loops over all the columns
df.iloc[:,i][df.isnull().iloc[:, i]]=df.mean().iloc[i] # subsets the df using the isnull() method, extracting the positions
# in each column where the
return(df)
此外,您的函数正在直接更改 df
。你可能要小心。我不确定那是你想要的。
说了这么多。我推荐另一种方法
def update(df):
return df.where(df.notnull(), df.mean(), axis=1)
您可以使用任意数量的方法来用均值填充缺失值。我建议使用@MaxU 的答案。
df.where
当第一个参数为 True
时采用 df
否则第二个参数为
df.where(df.notnull(), df.mean(), axis=1)
df.combine_first
用尴尬pandas
广播
df.combine_first(pd.DataFrame([df.mean()], df.index))
np.where
pd.DataFrame(
np.where(
df.notnull(), df.values,
np.nanmean(df.values, 0, keepdims=1)),
df.index, df.columns)
我创建了一个函数,用相应列的方法替换 Pandas 数据框中的 NaN。我用一个小的数据框测试了这个函数,它起作用了。当我将它应用于更大的数据框(30,000 行,9 列)时,我收到错误消息:IndexError: index out of bounds
函数如下:
# The 'update' function will replace all the NaNs in a dataframe with the mean of the respective columns
def update(df): # the function takes one argument, the dataframe that will be updated
ncol = df.shape[1] # number of columns in the dataframe
for i in range(0 , ncol): # loops over all the columns
df.iloc[:,i][df.isnull().iloc[:, i]]=df.mean()[i] # subsets the df using the isnull() method, extracting the positions
# in each column where the
return(df)
我用来测试功能的小数据框如下:
0 1 2 3
0 NaN NaN 3 4
1 NaN NaN 7 8
2 9.0 10.0 11 12
你能解释一下这个错误吗?我们将不胜感激您的建议。
我会使用DataFrame.fillna() method in conjunction with DataFrame.mean()方法:
In [130]: df.fillna(df.mean())
Out[130]:
0 1 2 3
0 9.0 10.0 3 4
1 9.0 10.0 7 8
2 9.0 10.0 11 12
平均值:
In [138]: df.mean()
Out[138]:
0 9.0
1 10.0
2 7.0
3 8.0
dtype: float64
你得到 "index out of bounds" 的原因是因为当 i
是应该是序数位置的迭代时,你正在分配值 df.mean()[i]
。 df.mean()
是一个 Series
,其索引是 df
的列。 df.mean()[something]
表示 something
最好是列名。但它们不是,这就是为什么您会收到错误消息的原因。
您的代码...已修复
def update(df): # the function takes one argument, the dataframe that will be updated
ncol = df.shape[1] # number of columns in the dataframe
for i in range(0 , ncol): # loops over all the columns
df.iloc[:,i][df.isnull().iloc[:, i]]=df.mean().iloc[i] # subsets the df using the isnull() method, extracting the positions
# in each column where the
return(df)
此外,您的函数正在直接更改 df
。你可能要小心。我不确定那是你想要的。
说了这么多。我推荐另一种方法
def update(df):
return df.where(df.notnull(), df.mean(), axis=1)
您可以使用任意数量的方法来用均值填充缺失值。我建议使用@MaxU 的答案。
df.where
当第一个参数为 True
时采用 df
否则第二个参数为
df.where(df.notnull(), df.mean(), axis=1)
df.combine_first
用尴尬pandas
广播
df.combine_first(pd.DataFrame([df.mean()], df.index))
np.where
pd.DataFrame(
np.where(
df.notnull(), df.values,
np.nanmean(df.values, 0, keepdims=1)),
df.index, df.columns)