根据条件对某些组进行转换以创建新的col

时间:2019-02-23 03:49:26

标签: python pandas pandas-groupby

分组依据后,是否有更高效的方法来执行以下操作?

对于每个group,我想获取value为<= 3的最大time

import numpy as np
import pandas as pd


d = dict(group=[1,1,1,1,1,2,2,2,2,2,3,3,3,3,3], times=[0,1,2,3,4]*3, values=np.random.rand(15))
df = pd.DataFrame.from_dict(d)

# e.g.:

    group  times    values
0       1      0  0.277623
1       1      1  0.227311
2       1      2  0.798941
3       1      3  0.861006
4       1      4  0.486385
5       2      0  0.543527
6       2      1  0.347159
7       2      2  0.138165
8       2      3  0.152132
9       2      4  0.402830
10      3      0  0.688038
11      3      1  0.450904
12      3      2  0.351267
13      3      3  0.195594
14      3      4  0.834823

以下内容似乎可行,但速度较慢且不够简洁:

for label, group in df.groupby(['group']):
    rows = group.index
    df.loc[rows,'new_value'] = group.loc[group.time <= 3, 'values'].max()

1 个答案:

答案 0 :(得分:2)

认为,您可以在分组之前使用where。为了获得更好的性能,请使用transform

df['new_value'] = df['values'].where(df.times < 3).groupby(df.group).transform('max')    
df

    group  times    values  new_value
0       1      0  0.271137   0.751412
1       1      1  0.262456   0.751412
2       1      2  0.751412   0.751412
3       1      3  0.364099   0.751412
4       1      4  0.462447   0.751412
5       2      0  0.022403   0.792396
6       2      1  0.792396   0.792396
7       2      2  0.181434   0.792396
8       2      3  0.106931   0.792396
9       2      4  0.226425   0.792396
10      3      0  0.425845   0.535085
11      3      1  0.527567   0.535085
12      3      2  0.535085   0.535085
13      3      3  0.194340   0.535085
14      3      4  0.958947   0.535085

这正是您当前代码返回的内容。


where确保我们不考虑时间大于3的值,因为max会忽略NaN。 groupby是根据此中间结果计算的。

df['values'].where(df.times <= 3)

0     0.271137
1     0.262456
2     0.751412
3     0.364099
4          NaN
5     0.022403
6     0.792396
7     0.181434
8     0.106931
9          NaN
10    0.425845
11    0.527567
12    0.535085
13    0.194340
14         NaN
Name: values, dtype: float64