如何加速Pandas DataFrame子集选择与统计量计算?
优化Pandas分组统计的效率问题
嘿,我太懂你这种情况了——嵌套循环遍历唯一值再反复切片DataFrame的操作,在数据量稍大的时候肯定会慢到让人抓狂!问题出在你每次循环都要全量扫描整个DataFrame做筛选,相当于把数据读了N遍(N是两个唯一值集合的乘积),这完全是在做重复功。
高效替代方案:用Pandas原生的groupby聚合
Pandas的groupby就是专门为这类分组统计场景设计的,内部做了大量优化,只需要扫描一次数据就能完成所有分组的统计计算,速度会快很多。
这里给你两种实现思路,都比循环高效得多:
方法1:一次性完成所有聚合操作
直接通过agg方法指定所有需要的统计量,代码更简洁:
# 先提前把column_name1转成int类型(避免循环里重复转换) df['column_name1'] = df['column_name1'].astype(int) # 按两个列分组,一次性计算求和、min/max/mean result = df.groupby(['column_name1', 'column_name2']).agg( # 对所有列求和 **{col: 'sum' for col in df.columns}, # 对amount列单独计算额外统计量 amount_min=('amount', 'min'), amount_max=('amount', 'max'), amount_mean=('amount', 'mean') )
方法2:拆分统计再合并(更直观)
如果觉得上面的字典推导有点绕,可以拆成两步计算再合并,逻辑更清晰:
# 提前转换数据类型 df['column_name1'] = df['column_name1'].astype(int) # 第一步:计算各分组的求和结果 sum_groups = df.groupby(['column_name1', 'column_name2']).sum() # 第二步:计算amount列的min/max/mean,并修改列名 amount_stats = df.groupby(['column_name1', 'column_name2'])['amount'].agg( ['min', 'max', 'mean'] ).rename(columns={ 'min': 'amount_min', 'max': 'amount_max', 'mean': 'amount_mean' }) # 合并两个结果 final_result = sum_groups.join(amount_stats)
为什么这个方法更快?
groupby会先对DataFrame做一次分组预处理,把每个(column_name1, column_name2)对应的行都归到一起,之后所有统计计算都是在分组后的子数据集上进行,不需要反复扫描全量数据。这种方式的时间复杂度是O(n)(n是数据行数),而你的原循环是O(nmk)(m、k是两个列的唯一值数量),效率差距会随着数据量增大越来越明显。
内容的提问来源于stack exchange,提问作者mrgloom
相关产品推荐
相关产品推荐

