为大尺寸数据框上的多列填充默认值的有效方法

时间:2019-08-06 09:15:39

标签: python python-3.x pandas dataframe default-value

我有一个大小为150万条记录的数据框obs。我想用默认值填写NA,如下所示。

obs = pd.DataFrame({'person_id' :[1,2,3],'obs_date':['12/31/2007','11/25/2009',np.nan],
       'hero_id':[2,4,np.nan],'date2':['12/31/2017',np.nan,'10/06/2015'],
       'heroine_id':[1,np.nan,5],'date3':['12/31/2027','11/25/2029',np.nan],
       'bud_source_value':[1250000,250000,np.nan],
       'prod__source_value':[10000,20000,np.nan]})

逻辑是根据列名填充3个默认值。

1)以id结尾的列-以0结尾的fillna

2)以value结尾的列-带有''(空白/空)的fillna

3)包含date的列-包含12/31/2000的fillna

尽管我下面的代码工作正常(基于SO建议),但是是否有固定方法?

%%timeit
c = obs.columns.str
c1 = c.endswith('id')
c2 = c.endswith('value')
c3 = c.contains('date')

obs_final = np.select([c1,c2,c3], [obs.fillna(0), obs.fillna(''), 
obs.fillna("12/31/2000")])
obs_final = pd.DataFrame(obs_final, columns=obs.columns)

需要19.5 s ± 303 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)-这正常吗?

反正有改进的地方吗?

2 个答案:

答案 0 :(得分:2)

使用DataFrame.loc选择列并使用fillna

obs.loc[:, c1] = obs.loc[:, c1].fillna(0)
obs.loc[:, c2] = obs.loc[:, c2].fillna('')
obs.loc[:, c3] = obs.loc[:, c3].fillna("12/31/2000")

答案 1 :(得分:1)

我不确定这是否会使它更快,但是您可以尝试

obs[obs.columns[c1]] = obs[obs.columns[c1]].fillna(0)
obs[obs.columns[c2]] = obs[obs.columns[c2]].fillna('')
obs[obs.columns[c3]] = obs[obs.columns[c3]].fillna("12/31/2000")