2017-05-08 126 views
1

我有这样一个数据帧:回填值熊猫系列当值相匹配的另一列

import numpy as np 

raw_data = {'surface': [np.nan, np.nan, 'round', 'square'], 
      'city': ['San Francisco', 'Miami', 'San Francisco', 'Miami']} 

df = pd.DataFrame(raw_data, columns = ['surface', 'city']) 

这看起来是这样的:

 surface city 
    0 NaN  San Francisco 
    1 NaN  Miami 
    2 round San Francisco 
    3 square Miami 

我需要旧金山排的最早实例是充满了'圆形',以及迈阿密早前的一排充满'方形'。使用.fillna(method ='bfill')将不会考虑其他列值,并且只需填满所有先前的行。

其结果将是:

 surface city 
    0 round San Francisco 
    1 square Miami 
    2 round San Francisco 
    3 square Miami 
+0

是否想用NaN填写来自同一城市的第一个真实价值? – Allen

回答

1

您可以使用groupby.bfill;通过城市栏目组数据帧,然后使用bfill

df.groupby('city').bfill() 

# surface   city 
#0 round San Francisco 
#1 square   Miami 
#2 round San Francisco 
#3 square   Miami 
+0

如果df没有排序,这项工作是否可行? – Allen

+0

如果我们假设pandas groupby是[stable],此解决方案将为每个城市的数据框执行* back fill *(http://stackoverflow.com/questions/39373820/is-pandas-dataframe-groupby-guaranteed-即将稳定),这可能是。 – Psidom

1

使用groupby() [基于从PSidom令人钦佩的答案加减]确实是关键点,但它可能会造成混乱更不用说什么bfill()做,因为它没有做你真正认为它做的。

让我们快速浏览一下文档here。 而不是像OP想要的那样回填数据,它实际上只是在下一列填写缺少的数据和非缺失数据。 在这种情况下,它与groupby()效果很好,而你也需要做groupby('*your group*').ffill()的前向填充,以防你的数据更加复杂。

为了进一步说明,让我们来修改你这样的数据:

import numpy as np 
import pandas as pd 

raw_data = {'surface': [np.nan, np.nan, 'round', 'square', np.nan, np.nan, np.nan, np.nan], 
      'city': ['San Francisco', 'Miami', 'San Francisco', 'Miami', 'Miami', 'Miami', 'San Francisco', 'Miami']} 
df = pd.DataFrame(raw_data, columns = ['surface', 'city']) 
df 

# surface city 
#0 NaN  San Francisco 
#1 NaN  Miami 
#2 round San Francisco 
#3 square Miami 
#4 NaN  Miami 
#5 NaN  Miami 
#6 NaN  San Francisco 
#7 NaN  Miami 

由于只有df.groupby('city').bfill(),你会拥有:

df2 = df.groupby('city').bfill() 
df2 

# surface city 
#0 round San Francisco 
#1 square Miami 
#2 round San Francisco 
#3 square Miami 
#4 NaN  Miami 
#5 NaN  Miami 
#6 NaN  San Francisco 
#7 NaN  Miami 

上有什么情况吗? bfill()在第0行和第1行做了工作,但保持第4〜7行不变。您应该同时使用bfill()ffill()。也许是这样的:

df3 = df2.groupby('city').ffill() 
df3 

# surface city 
#0 round San Francisco 
#1 square Miami 
#2 round San Francisco 
#3 square Miami 
#4 square Miami 
#5 square Miami 
#6 round San Francisco 
#7 square Miami 

要注意,你不应该使用像df.groupby('city').bfill().ffill()之类的东西。它会填写错误的地方。