pandas group by,在输入列上使用多个agg函数聚合

时间:2017-05-16 19:41:11

标签: python r pandas

我希望在数据帧上对pandas group做一些聚合,我需要在多个列上应用几个不同的自定义函数。这个操作在R中非常简单和习惯(使用data.tabledplyr),但我很惊讶我在熊猫中发现它很难:

import pandas as pd
data = pd.DataFrame({'A':[1,2,3,4,5,6],'B':[2,4,6,8,10,12],'C':[1,1,1,2,2,2]})

#These work
data.groupby('C').apply(lambda x: x.A.mean() - x.B.mean())
data.groupby('C').agg(['mean','std'])

#but this doesn't
data.groupby('C').agg([lambda x: x.A.mean() - x.B.mean(),
                       lambda x: len(x.A)])

我想计算一个统计量,但也要计算每个组中的样本大小,这似乎应该是一行或两行解决方案,但我有时也需要在分组数据框的多个列上应用多个函数。 / p>

2 个答案:

答案 0 :(得分:3)

我们可以编写一个在多个列上执行自定义函数的函数,并将结果作为数据框返回。

>>> def meandiff_length(data):
            data['mean_diff'] = data.A.mean() - data.B.mean()
            data['a_length'] = len(data.A)
            return data

我们可以对数据进行分组,并将自定义功能分别应用于组。

>>> data.groupby('C').apply(meandiff_length)
   A   B  C  mean_diff  a_length
0  1   2  1       -2.0         3
1  2   4  1       -2.0         3
2  3   6  1       -2.0         3
3  4   8  2       -5.0         3
4  5  10  2       -5.0         3
5  6  12  2       -5.0         3

此特定自定义函数在每一行中返回相同的值,因此使用drop_duplicates可能是您感兴趣的。但是,这是一个通用的解决方案,当我们的自定义函数变得更复杂时也可以使用。

答案 1 :(得分:3)

如果你需要单行,你可以这样做:

#use apply instead of agg to create multiple columns
data.groupby('C').apply(lambda x: pd.Series([x.A.mean() - x.B.mean(), len(x.A)])).rename(columns={0:'diff',1:'a_len'})
Out[2346]: 
   diff  a_len
C             
1  -2.0    3.0
2  -5.0    3.0

另一种不使用重命名的解决方案。

data.groupby('C').apply(lambda x: pd.DataFrame([[x.A.mean() - x.B.mean(), len(x.A)]],columns=['diff','a_len']))
Out[24]: 
     diff  a_len
C               
1 0  -2.0      3
2 0  -5.0      3