【问题标题】:pandas: Filling missing values within a grouppandas:填充组内的缺失值
【发布时间】:2018-03-03 17:51:46
【问题描述】:

我有一些实验数据,在每个试验中都有一些单个值,用NA 包围,我想填写整个试验:

df = pd.DataFrame({'trial': [1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3], 
    'cs_name': [np.nan, 'A1', np.nan, np.nan, np.nan, np.nan, 'B2', 
                np.nan, 'A1', np.nan, np.nan, np.nan]})
Out[177]: 
   cs_name  trial
0      NaN      1
1       A1      1
2      NaN      1
3      NaN      1
4      NaN      2
5      NaN      2
6       B2      2
7      NaN      2
8       A1      3
9      NaN      3
10     NaN      3
11     NaN      3

我可以使用bfill()ffill() 在整个试验中填充这些值,但我想知道是否有更好的方法来实现这一点。

df['cs_name'] = df.groupby('trial')['cs_name'].ffill()
df['cs_name'] = df.groupby('trial')['cs_name'].bfill()

预期输出:

   cs_name  trial
0       A1      1
1       A1      1
2       A1      1
3       A1      1
4       B2      2
5       B2      2
6       B2      2
7       B2      2
8       A1      3
9       A1      3
10      A1      3
11      A1      3

【问题讨论】:

    标签: python pandas


    【解决方案1】:

    另一种方法是使用first_valid_indextransform

    In [11]: g = df.groupby('trial')
    
    In [12]: g['cs_name'].transform(lambda s: s.loc[s.first_valid_index()])
    Out[12]: 
    0     A1
    1     A1
    2     A1
    3     A1
    4     B2
    5     B2
    6     B2
    7     B2
    8     A1
    9     A1
    10    A1
    11    A1
    Name: cs_name, dtype: object
    

    这应该比使用 ffill 后跟 bfill 更有效...

    并使用它来更改cs_name 列:

    df['cs_name'] = g['cs_name'].transform(lambda s: s.loc[s.first_valid_index()])
    

    注意:我认为有一个方法来抓取 pandas 中的第一个非空对象会是一个很好的增强,在 numpy 中它是an open request,我认为目前没有方法(我可能是错的!)...

    【讨论】:

      【解决方案2】:

      如果您想避免某些组仅包含 NaN 时出现的错误,您可以执行以下操作(请注意,我更改了 df,因此具有 trial=1 的组只有 Nan):

      df = pd.DataFrame({'trial': [1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3,1,1], 
      'cs_name': [np.nan, np.nan, np.nan, np.nan, np.nan, np.nan, 'B2', np.nan, 
      'A3', np.nan, np.nan, np.nan, np.nan,np.nan]})
      
      g = data.groupby('trial')
      
      g['cs_name'].transform(lambda s: 'No values to aggregate' if 
          pd.isnull(s).all() == True else s.loc[s.first_valid_index()])
      
      df['cs_name'] = g['cs_name'].transform(lambda s: 'No values to aggregate' if 
          pd.isnull(s).all() == True else s.loc[s.first_valid_index()])`
      

      这样,当程序找到特定组的所有 NaN 时,您输入“没有要聚合的值”(或任何您想要的),而不是错误。

      希望这会有所帮助:)

      费德里科

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2016-03-15
        • 1970-01-01
        • 2016-08-26
        • 2015-01-08
        • 1970-01-01
        • 2013-04-27
        相关资源
        最近更新 更多