принимая первый non null в python
Я пытаюсь получить первое ненулевое значение из нескольких серий панд в фрейме данных.
df = pd.DataFrame({'a':[2, np.nan, np.nan, np.nan],
'b':[np.nan, 5, np.nan, np.nan],
'c':[np.nan, 55, 13, 14],
'd':[np.nan, np.nan, np.nan, 4],
'e':[12, np.nan, np.nan, 22],
})
a b c d e
0 2.0 NaN NaN NaN 12.0
1 NaN 5.0 55.0 NaN NaN
2 NaN NaN 13.0 NaN NaN
3 NaN NaN 14.0 4.0 22.0
в этой df
Я хочу создать новый столбец 'f'
, и установите его равным 'a'
если a не равно null,'b'
если b не равно null и т. д. вплоть до е.
я мог бы сделать кучу np.где утверждения, которые неэффективны.
df['f'] = np.where(df.a.notnull(), df.a,
np.where(df.b.notnull(), df.b,
etc.))
Я заглянул в doing df.a or df.b or df.c
etc.
результат должен выглядеть так:
a b c d e f
0 2.0 NaN NaN NaN 12.0 2
1 NaN 5.0 55.0 NaN NaN 5
2 NaN NaN 13.0 NaN NaN 13
3 NaN NaN 14.0 4.0 22.0 14
3 ответов
решение
df.groupby(['f']*df.shape[1], axis=1).first()
Out[385]:
f
0 2.0
1 5.0
2 13.0
3 14.0
другого
df.bfill(1)['a']
Out[388]:
0 2.0
1 5.0
2 13.0
3 14.0
Name: a, dtype: float64
вы также можете использовать first_valid_index
In [336]: df.apply(lambda x: x.loc[x.first_valid_index()], axis=1)
Out[336]:
0 2.0
1 5.0
2 13.0
3 14.0
dtype: float64
или stack
и groupby
In [359]: df.stack().groupby(level=0).first()
Out[359]:
0 2.0
1 5.0
2 13.0
3 14.0
dtype: float64
или first_valid_index
в поиске
In [355]: df.lookup(df.index, df.apply(pd.Series.first_valid_index, axis=1))
Out[355]: array([ 2., 5., 13., 14.])
вы также можете использовать numpy
для этого:
first_valid = (~np.isnan(df.values)).argmax(1)
затем использовать индексирование:
df.assign(valid=df.values[range(len(first_valid)), first_valid])
a b c d e valid
0 2.0 NaN NaN NaN 12.0 2.0
1 NaN 5.0 55.0 NaN NaN 5.0
2 NaN NaN 13.0 NaN NaN 13.0
3 NaN NaN 14.0 4.0 22.0 14.0