如何在 pandas 中聚合子数据帧?

How do I aggregate sub-dataframes in pandas?

假设我有两级多索引数据框

In [1]: index = pd.MultiIndex.from_tuples([(i,j)  for i in range(3)
      :                                           for j in range(1+i)], names=list('ij') )
      : df = pd.DataFrame(0.1*np.arange(2*len(index)).reshape(-1,2),
      :                   columns=list('xy'), index=index )
      : df
Out[1]:
      x    y
i j
0 0  0.0  0.1
1 0  0.2  0.3
  1  0.4  0.5
2 0  0.6  0.7
  1  0.8  0.9
  2  1.0  1.1

我想 运行 每个子数据帧上的自定义函数:

In [2]: def my_aggr_func(subdf):
      :     return subdf['x'].mean() / subdf['y'].mean()
      :
      : level0 = df.index.levels[0].values
      : pd.DataFrame({'mean_ratio': [my_aggr_func(df.loc[i]) for i in level0]},
      :              index=pd.Index(level0, name=index.names[0]) )
Out[2]:
     mean_ratio
i
0    0.000000
1    0.750000
2    0.888889

有没有一种优雅的方法可以用 df.groupby('i').agg(__something__) 或类似的东西来做到这一点?

需要 GroupBy.apply,与 DataFrame:

一起工作
df1 = df.groupby('i').apply(my_aggr_func).to_frame('mean_ratio')
print (df1)
   mean_ratio
i            
0    0.000000
1    0.750000
2    0.888889

您不需要自定义函数。您可以使用 agg 计算 'within group means',然后执行 eval 以获得您想要的比率。

df.groupby('i').agg('mean').eval('x / y')

i
0    0.000000
1    0.750000
2    0.888889
dtype: float64