2017-01-26 116 views
2

我有一個熊貓DataFrame。我試圖根據「科室」欄中相應級別的平均價格填寫「價格」列的南瓜。什麼是高效和優雅的方式來做到這一點?我的數據看起來像這樣基於另一列的平均值填充列的值

Name Sex Section Price 
Joe  M  1  2 
Bob  M  1  nan 
Nancy F  2  5 
Grace F  1  6 
Jen  F  2  3 
Paul M  2  nan 

回答

5

您可以使用組合groupby,transformmean。請注意,我修改了您的示例,因爲否則兩個部分的平均值都相同。從

In [21]: df 
Out[21]: 
    Name Sex Section Price 
0 Joe M  1 2.0 
1 Bob M  1 NaN 
2 Nancy F  2 5.0 
3 Grace F  1 6.0 
4 Jen F  2 10.0 
5 Paul M  2 NaN 

開始,我們可以使用

df["Price"] = (df["Price"].fillna(df.groupby("Section")["Price"].transform("mean")) 

生產

In [23]: df 
Out[23]: 
    Name Sex Section Price 
0 Joe M  1 2.0 
1 Bob M  1 4.0 
2 Nancy F  2 5.0 
3 Grace F  1 6.0 
4 Jen F  2 10.0 
5 Paul M  2 7.5 

這工作,因爲我們可以通過計算節均值:

In [29]: df.groupby("Section")["Price"].mean() 
Out[29]: 
Section 
1 4.0 
2 7.5 
Name: Price, dtype: float64 
使用

和廣播這個備份到一個完整的系列,我們可以傳遞給fillna():

In [30]: df.groupby("Section")["Price"].transform("mean") 
Out[30]: 
0 4.0 
1 4.0 
2 7.5 
3 4.0 
4 7.5 
5 7.5 
Name: Price, dtype: float64 
0

「相應的水平」我假設你的意思是相等的部分值。

如果是這樣,你可以通過

for section_value in sorted(set(df.Section)): 

    df.loc[df['Section']==section_value, 'Price'] = df.loc[df['Section']==section_value, 'Price'].fillna(df.loc[df['Section']==section_value, 'Price'].mean()) 

希望它可以幫助解決這個問題!和平

1

pandas手術,但速度慢

參考@ DSM的回答,以便更快pandas解決方案

這是一種更爲手術的方法,可以提供一些視角,可能有用

  • 使用groupyby

    • 計算我們mean每個Section

      means = df.groupby('Section').Price.mean() 
      
  • 識別空

    • 使用isnull使用布爾切片

      nulls = df.Price.isnull() 
      
  • 使用map

    • 切片Section列,以限制只是那些行與空Price

      fills = df.Section[nulls].map(means) 
      
  • 使用loc

    • 填充在df斑點僅在零點是

      df.loc[nulls, 'Price'] = fills 
      

總之

means = df.groupby('Section').Price.mean() 
nulls = df.Price.isnull() 
fills = df.Section[nulls].map(means) 
df.loc[nulls, 'Price'] = fills 

print(df) 

    Name Sex Section Price 
0 Joe M  1 2.0 
1 Bob M  1 4.0 
2 Nancy F  2 5.0 
3 Grace F  1 6.0 
4 Jen F  2 10.0 
5 Paul M  2 7.5 
+0

尼斯後,易懂+1 – ade1e