Python:Groupby 第一个非 NaN 值

fre*_*888 1 python pandas

我有以下数据框:

id    number   
1      13
1      13
1      NaN
1      NaN
2      11
2      11
2      11
2      NaN
Run Code Online (Sandbox Code Playgroud)

我想找到每个 id 的第一个非 NaN 值并将其标记为 1。结果应如下所示:

id    number     code   
1      13         NaN
1      13         1
1      NaN        NaN
1      NaN        NaN
2      11         NaN
2      11         NaN
2      11         1
2      NaN        NaN
Run Code Online (Sandbox Code Playgroud)

我尝试了以下命令,然后从那里开始:

df["test"] = df.groupby("id")["number"].first_valid_index()
Run Code Online (Sandbox Code Playgroud)

它给了我以下错误:无法访问“SeriesGroupBy”对象的可调用属性“first_valid_index”,请尝试使用“apply”方法

然后我尝试了这个:

df['test'] = df.groupby("id")['number'].apply(lambda x: x.first_valid_index())
Run Code Online (Sandbox Code Playgroud)

但这给了我一列 Nats ......

有人知道如何有效地解决问题吗?

cs9*_*s95 5

假设您的意思是last_valid_index,您可以apply使用last_valid_index函数并loc分配-

df.loc[df.groupby('id').number.apply(pd.Series.last_valid_index), 'code'] = 1
df

   id  number  code
0   1    13.0   NaN
1   1    13.0   1.0
2   1     NaN   NaN
3   1     NaN   NaN
4   2    11.0   NaN
5   2    11.0   NaN
6   2    11.0   1.0
7   2     NaN   NaN
Run Code Online (Sandbox Code Playgroud)

或者,使用groupby+ idxmax-

df.loc[df.number.notnull().cumsum().groupby(df.id).idxmax(), 'code'] = 1
df

   id  number  code
0   1    13.0   NaN
1   1    13.0   1.0
2   1     NaN   NaN
3   1     NaN   NaN
4   2    11.0   NaN
5   2    11.0   NaN
6   2    11.0   1.0
7   2     NaN   NaN
Run Code Online (Sandbox Code Playgroud)