使用最接近缺失值的日期的值来填充缺失值

时间:2019-11-11 21:47:45

标签: python pandas missing-data

我知道如何将groupby方法与ffill或bfill一起使用以估算缺少的值。但是我的问题是,我需要首先在“日期”列中找到与“得分”列中的空值最接近的日期,如果分数列中的值不为空,则用该值进行插补。如果该值为空,则需要搜索另一个最近的日期。我可以遍历行并执行此操作,但是速度非常慢。

这是数据的示例:

df = pd.DataFrame(
     {'cn': [1, 1, 1, 1, 2, 2, 2], 
      'date': ['01/10/2017', '02/09/2016', '02/10/2016','01/20/2017', '05/15/2019', '02/10/2016', '02/10/2017'],
      'score': [np.nan, np.nan, 6, 5, 4, np.nan, 8]})

    cn  date    score
0   1   01/10/2017  NaN
1   1   02/09/2016  NaN
2   1   02/10/2016  6
3   1   01/20/2017  5
4   2   05/15/2019  4
5   2   02/10/2016  NaN
6   2   02/10/2017  8.0

输出应为

    cn  date    score
0   1   01/10/2017  5
1   1   02/09/2016  6
2   1   02/10/2016  6
3   1   01/20/2017  5
4   2   05/15/2017  4
5   2   02/10/2016  8
6   2   02/10/2018  8

如何使用groupby方法和apply函数来做到这一点?

1 个答案:

答案 0 :(得分:5)

使用pd.merge_asof获得最接近的系列,然后仅.fillna。有一些操作可以确保最后对齐索引。

import pandas as pd

df['date'] = pd.to_datetime(df.date) 

s = (pd.merge_asof(
         df.sort_values('date').reset_index(),            # Full Data Frame
         df.sort_values('date').dropna(subset=['score']), # Subset with valid scores
         by='cn',                                         # Only within `'cn'` group
         on='date', direction='nearest'                   # Match closest date 
                  )
       .set_index('index')
       .score_y)

df['score'] = df.score.fillna(s, downcast='infer')

输出:df

   cn       date  score
0   1 2017-01-10      5
1   1 2016-02-09      6
2   1 2016-02-10      6
3   1 2017-01-20      5
4   2 2019-05-15      4
5   2 2016-02-10      8
6   2 2017-02-10      8