簡體   English   中英

Pandas 從另一個 dataframe 填充 dataframe 中的缺失值

[英]Pandas fill missing values in dataframe from another dataframe

我找不到 pandas function(我以前見過)來用另一個 dataframe 中的值替換 dataframe 中的 NaN(假設可以指定一個公共索引)。 有什么幫助嗎?

如果您有兩個相同形狀的 DataFrame,則:

df[df.isnull()] = d2

會做的伎倆。

視覺表現

只有df.isnull()評估為True (以綠色突出顯示)的位置才有資格分配。

實際上,DataFrame 的大小/形狀並不總是相同,轉換方法(尤其是.shift() )很有用。

傳入的數據總是臟的、不完整的或不一致的。 課程標准。 有一個非常廣泛的 Pandas教程和相關的食譜來處理這些情況。

正如我剛剛了解到的,有一個DataFrame.combine_first()方法,它正是這樣做的,具有附加屬性,如果您更新的數據框d2大於原始df ,則還會添加額外的行和列。

df = df.combine_first(d2)

這應該很簡單

df.fillna(d2)

一個專門的方法是DataFrame.update

引用自文檔:

使用來自另一個 DataFrame 的非 NA 值就地修改。
在索引上對齊。 沒有返回值。

需要注意的是,此方法將就地修改您的數據。 所以它會覆蓋你更新的數據框。

示例

print(df1)
       A    B     C
aaa  NaN  1.0   NaN
bbb  NaN  NaN  10.0
ccc  3.0  NaN   6.0
ddd  NaN  NaN   NaN
eee  NaN  NaN   NaN

print(df2)
         A    B     C
index                
aaa    1.0  1.0   NaN
bbb    NaN  NaN  10.0
eee    NaN  1.0   NaN

# update df1 NaN where there are values in df2
df1.update(df2)
print(df1)
       A    B     C
aaa  1.0  1.0   NaN
bbb  NaN  NaN  10.0
ccc  3.0  NaN   6.0
ddd  NaN  NaN   NaN
eee  NaN  1.0   NaN

注意在aaa, Aeee, B相交處更新的NaN

DataFrame.combine_first()准確地回答了這個問題。

但是,有時您想用 DataFrame B 中的值填充/替換/覆蓋 DataFrame A 的一些非缺失(非 NaN)值。這個問題讓我來到了這個頁面,解決方案是DataFrame.mask()

A = B.mask(condition, A)

condition為真時,將使用 A 的值,否則將使用 B 的值。

例如,您可以使用mask解決 OP 的原始問題,以便當 A 中的元素為非 NaN 時,使用它,否則使用 B 中的相應元素。

但是使用DataFrame.mask()你可以用 B 的值替換不符合任意標准(小於零?大於 100?)的 A 值。所以mask更靈活,對於這個問題來說太過分了,但我認為值得一提(我需要它來解決我的問題)。

同樣重要的是要注意 B 可能是一個 numpy 數組而不是 DataFrame。 DataFrame.combine_first()要求 B 是 DataFrame,但DataFrame.mask()只要求 B 是 NDFrame 並且其尺寸與 A 的尺寸匹配。

其他答案中缺少的一個重要信息是combine_firstfillna都匹配索引,因此您必須使索引在 DataFrame 中匹配才能使這些方法起作用。

通常,需要匹配其他一些列來填充缺失值。 那樣的話,就需要先用set_index來使要匹配的列,即索引。

df1 = df1.set_index(cols_to_be_matched).fillna(df2.set_index(cols_to_be_matched)).reset_index()

要么

df1 = df1.set_index(cols_to_be_matched).combine_first(df2.set_index(cols_to_be_matched)).reset_index()

另一種選擇是使用merge

df1 = (df1.merge(df2, on=cols_to_be_matched, how='left', suffixes=('','\x00'))
       .sort_index(axis=1).bfill(axis=1)[df.columns])

這里的想法是左合並並通過對列進行排序(我們使用'\x00'作為df2中列的后綴,因為它是具有最低 Unicode 值的字符),我們確保相同的列值在每個列的旁邊結束其他。 然后水平使用bfill以使用df2中的值更新df1


例子:

假設你有df1

   C1 C2   C3  C4
0   1  a  1.0   0
1   1  b  NaN   1
2   2  b  NaN   2
3   2  b  NaN   3

df2

   C1 C2  C3
0   1  b   2
1   2  b   3

並且您想用df2中的值為每對C1 - C2值對填充df1中的缺失值。 然后

cols_to_be_matched = ['C1', 'C2']

並且上面的所有代碼都會產生以下輸出(其中確實根據需要填充了值):

   C1 C2   C3  C4
0   1  a  1.0   0
1   1  b  2.0   1
2   2  b  3.0   2
3   2  b  3.0   3

暫無
暫無

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

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