Python实现类Excel AVERAGEIF逐行均值计算的高效方案问询
高效实现:用Pandas的
transform完成分组均值映射到每行 你的问题本质是将分组聚合的结果广播回原DataFrame的每一行,这正是Pandas中transform方法的设计场景!相比你手动遍历的方式,transform是完全向量化的操作,内部用Cython优化,处理20万行数据毫无压力,代码也更简洁。
直接上最优解代码
首先是你的示例数据:
import pandas as pd df = pd.DataFrame({ 'key1': ['a', 'b', 'a', 'a'], 'key2': ['c', 'd', 'a', 'a'], 'number': [100, 200, 150, 200] })
不需要手动拼接key1和key2,直接按两个组合键分组,然后用transform('mean')就能把均值映射到每一行:
# 新增一列存储每行对应的分组均值 df['group_avg'] = df.groupby(['key1', 'key2'])['number'].transform('mean') # 查看结果 print(df)
输出结果:
key1 key2 number group_avg 0 a c 100 100.0 1 b d 200 200.0 2 a a 150 175.0 3 a a 200 175.0
如果只需要单独的均值列表,直接提取列转成列表即可:
avgif = df['group_avg'].tolist() # 结果:[100.0, 200.0, 175.0, 175.0]
为什么这个方法比你的原方案高效?
你的原方案需要手动拼接键,然后通过Python循环逐个查找聚合结果,这在数据量达到20万行时,Python层面的循环会带来巨大的性能开销。而transform是Pandas的内置向量化操作,完全避开了Python循环,底层用C语言级别的逻辑处理,速度能提升几十甚至上百倍。
备选方案:用merge实现(不如transform简洁)
如果你想了解其他思路,也可以先分组聚合得到均值,再通过merge合并回原DataFrame,但代码会比transform繁琐一些:
# 先获取分组均值并重置索引 grouped_mean = df.groupby(['key1', 'key2'])['number'].mean().reset_index(name='group_avg') # 合并回原DataFrame df = df.merge(grouped_mean, on=['key1', 'key2'])
但这个方法需要额外的合并步骤,效率和简洁性都不如transform,所以优先推荐前者。
总结
处理这类“分组聚合后映射回原行”的需求,groupby.transform是Pandas的标准解决方案,完美适配大数据量场景,代码简洁且性能拉满,完全替代你手动遍历的低效逻辑。
内容的提问来源于stack exchange,提问作者jesse
相关产品推荐
相关产品推荐

