簡體   English   中英

pandas DataFrame:用列的平均值替換 nan 值

[英]pandas DataFrame: replace nan values with average of columns

我有一個主要填充實數的 Pandas DataFrame,但其中也有一些nan值。

如何用它們所在的列的平均值替換nan

這個問題與這個問題非常相似: numpy array:replace nan values with average of columns但不幸的是,那里給出的解決方案不適用於pandas DataFrame。

您可以簡單地使用DataFrame.fillna直接填充nan

In [27]: df 
Out[27]: 
          A         B         C
0 -0.166919  0.979728 -0.632955
1 -0.297953 -0.912674 -1.365463
2 -0.120211 -0.540679 -0.680481
3       NaN -2.027325  1.533582
4       NaN       NaN  0.461821
5 -0.788073       NaN       NaN
6 -0.916080 -0.612343       NaN
7 -0.887858  1.033826       NaN
8  1.948430  1.025011 -2.982224
9  0.019698 -0.795876 -0.046431

In [28]: df.mean()
Out[28]: 
A   -0.151121
B   -0.231291
C   -0.530307
dtype: float64

In [29]: df.fillna(df.mean())
Out[29]: 
          A         B         C
0 -0.166919  0.979728 -0.632955
1 -0.297953 -0.912674 -1.365463
2 -0.120211 -0.540679 -0.680481
3 -0.151121 -2.027325  1.533582
4 -0.151121 -0.231291  0.461821
5 -0.788073 -0.231291 -0.530307
6 -0.916080 -0.612343 -0.530307
7 -0.887858  1.033826 -0.530307
8  1.948430  1.025011 -2.982224
9  0.019698 -0.795876 -0.046431

fillna的文檔字符串說value應該是標量或字典,但是,它似乎也適用於Series 如果你想傳遞一個字典,你可以使用df.mean().to_dict()

嘗試:

sub2['income'].fillna((sub2['income'].mean()), inplace=True)
In [16]: df = DataFrame(np.random.randn(10,3))

In [17]: df.iloc[3:5,0] = np.nan

In [18]: df.iloc[4:6,1] = np.nan

In [19]: df.iloc[5:8,2] = np.nan

In [20]: df
Out[20]: 
          0         1         2
0  1.148272  0.227366 -2.368136
1 -0.820823  1.071471 -0.784713
2  0.157913  0.602857  0.665034
3       NaN -0.985188 -0.324136
4       NaN       NaN  0.238512
5  0.769657       NaN       NaN
6  0.141951  0.326064       NaN
7 -1.694475 -0.523440       NaN
8  0.352556 -0.551487 -1.639298
9 -2.067324 -0.492617 -1.675794

In [22]: df.mean()
Out[22]: 
0   -0.251534
1   -0.040622
2   -0.841219
dtype: float64

每列應用該列的平均值並填充

In [23]: df.apply(lambda x: x.fillna(x.mean()),axis=0)
Out[23]: 
          0         1         2
0  1.148272  0.227366 -2.368136
1 -0.820823  1.071471 -0.784713
2  0.157913  0.602857  0.665034
3 -0.251534 -0.985188 -0.324136
4 -0.251534 -0.040622  0.238512
5  0.769657 -0.040622 -0.841219
6  0.141951  0.326064 -0.841219
7 -1.694475 -0.523440 -0.841219
8  0.352556 -0.551487 -1.639298
9 -2.067324 -0.492617 -1.675794

如果您想用均值來估算缺失值並且想要逐列進行,那么這只會用該列的均值來估算。 這可能更具可讀性。

sub2['income'] = sub2['income'].fillna((sub2['income'].mean()))
# To read data from csv file
Dataset = pd.read_csv('Data.csv')

X = Dataset.iloc[:, :-1].values

# To calculate mean use imputer class
from sklearn.impute import SimpleImputer
imputer = SimpleImputer(missing_values=np.nan, strategy='mean')
imputer = imputer.fit(X[:, 1:3])
X[:, 1:3] = imputer.transform(X[:, 1:3])

直接使用df.fillna(df.mean())用均值填充所有空值

如果你想用該列的平均值填充空值,那么你可以使用這個

假設x=df['Item_Weight']這里Item_Weight是列名

在這里我們分配(用 x 的平均值填充 x 的空值到 x 中)

df['Item_Weight'] = df['Item_Weight'].fillna((df['Item_Weight'].mean()))

如果你想用一些字符串填充空值,然后使用

這里Outlet_size是列名

df.Outlet_Size = df.Outlet_Size.fillna('Missing')

雖然,下面的代碼完成了這項工作,但它的性能受到了很大的打擊,因為你處理一個帶有 # 記錄 100k 或更多的 DataFrame:

df.fillna(df.mean())

根據我的經驗,應該只在需要的地方替換 NaN 值(無論是用 Mean 還是 Median) ,而不是在整個 DataFrame 上應用 fillna()

我有一個包含 20 個變量的 DataFrame,其中只有 4 個需要 NaN 值處理(替換)。 我嘗試了上面的代碼(代碼 1),以及它的一個稍微修改過的版本(代碼 2),我有選擇地運行它。即僅在具有 NaN 值的變量上運行

#------------------------------------------------
#----(Code 1) Treatment on overall DataFrame-----

df.fillna(df.mean())

#------------------------------------------------
#----(Code 2) Selective Treatment----------------

for i in df.columns[df.isnull().any(axis=0)]:     #---Applying Only on variables with NaN values
    df[i].fillna(df[i].mean(),inplace=True)

#---df.isnull().any(axis=0) gives True/False flag (Boolean value series), 
#---which when applied on df.columns[], helps identify variables with NaN values

以下是我觀察到的性能,因為我不斷增加 DataFrame 中的 # 記錄

具有約 10 萬條記錄的數據幀

  • 代碼 1:22.06 秒
  • 代碼 2:0.03 秒

具有約 20 萬條記錄的數據幀

  • 代碼 1:180.06 秒
  • 代碼 2:0.06 秒

具有約 160 萬條記錄的 DataFrame

  • 代碼 1:代碼無休止地運行
  • 代碼 2:0.40 秒

具有約 1300 萬條記錄的 DataFrame

  • 代碼 1:--在看到 160 萬條記錄的性能后,甚至沒有嘗試--
  • 代碼 2:3.20 秒

抱歉回答太長! 希望這可以幫助 !

除了上述選項之外的另一個選項是:

df = df.groupby(df.columns, axis = 1).transform(lambda x: x.fillna(x.mean()))

它不如之前的均值響應優雅,但如果您希望用其他列函數替換空值,它可能會更短。

Pandas:如何用一列的平均值(均值)、中位數或其他統計數據替換 NaN ( nan ) 值

假設您的 DataFrame 是df並且您有一列名為nr_items 這是: df['nr_items']

如果要將df['nr_items']列的NaN替換為該列的平均值

使用方法.fillna()

mean_value=df['nr_items'].mean()
df['nr_item_ave']=df['nr_items'].fillna(mean_value)

我創建了一個新的df稱為列nr_item_ave存儲與新列NaN被替換值mean列的值。

使用mean時應該小心。 如果您有異常值更推薦使用中median

使用sklearn庫預處理類

from sklearn.impute import SimpleImputer
missingvalues = SimpleImputer(missing_values = np.nan, strategy = 'mean', axis = 0)
missingvalues = missingvalues.fit(x[:,1:3])
x[:,1:3] = missingvalues.transform(x[:,1:3])

注意:在最近的版本中,參數missing_values值從NaN更改為np.nan

我使用此方法按列的平均值填充缺失值。

fill_mean = lambda col : col.fillna(col.mean())

df = df.apply(fill_mean, axis = 0)

您還可以使用value_counts來獲取最頻繁的值。 這適用於不同的數據類型。

df = df.apply(lambda x:x.fillna(x.value_counts().index[0]))

是 value_counts api 參考。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM