You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

多列GroupBy组合获取Top值及无对应组合时的异常处理问询

关于Pandas GroupBy的两个常见问题解决方案

1. 如何使用不同的GroupBy组合获取浏览量最高的记录

假设我们有如下模拟用户行为的样例数据:

import pandas as pd

data = {
    'married': ['yes', 'yes', 'no', 'no', 'yes', 'no'],
    'gender': ['male', 'female', 'male', 'female', 'male', 'female'],
    'age_group': ['young', 'young', 'old', 'young', 'old', 'old'],
    'occupation': ['student', 'teacher', 'engineer', 'student', 'teacher', 'engineer'],
    'views': [150, 200, 300, 180, 250, 280],
    'rating': [4.2, 4.5, 4.8, 4.3, 4.7, 4.6]
}
df = pd.DataFrame(data)

不同GroupBy组合的实现方式

方式一:groupby().idxmax() + 索引定位

先通过分组找到每组浏览量最大的行索引,再用索引提取对应记录,这是最直接的方法:

  • 单分组(按married分组)
# 获取每个婚姻状态下浏览量最高的记录
max_views_single = df.loc[df.groupby('married')['views'].idxmax()]
print(max_views_single)

输出:

married  gender age_group occupation  views  rating
2      no    male       old   engineer    300     4.8
4     yes    male       old    teacher    250     4.7
  • 多分组(按married+gender分组)
# 获取每个婚姻状态+性别组合下浏览量最高的记录
max_views_multi = df.loc[df.groupby(['married', 'gender'])['views'].idxmax()]
print(max_views_multi)

输出:

married  gender age_group occupation  views  rating
4     yes    male       old    teacher    250     4.7
1     yes  female     young    teacher    200     4.5
2      no    male       old   engineer    300     4.8
5      no  female       old   engineer    280     4.6

方式二:sort_values() + drop_duplicates()

先按分组列和浏览量降序排序,再保留每个分组的第一条记录,适合需要自定义排序逻辑的场景:

# 按married+age_group分组取最高浏览量
max_views_sort = df.sort_values(['married', 'age_group', 'views'], ascending=[True, True, False])\
                   .drop_duplicates(['married', 'age_group'])
print(max_views_sort)

输出:

married  gender age_group occupation  views  rating
5      no  female       old   engineer    280     4.6
3      no  female     young    student    180     4.3
4     yes    male       old    teacher    250     4.7
1     yes  female     young    teacher    200     4.5

2. 多列GroupBy获取评分最高记录时,处理不存在的分组组合

问题场景还原

假设我们想要获取(married='yes', gender='male', age_group='young', occupation='teacher')这个组合的最高评分记录,但当前数据里没有这个组合,直接用get_group会触发KeyError:

# 尝试获取不存在的分组组合,会报错
grouped = df.groupby(['married', 'gender', 'age_group', 'occupation'])
try:
    grouped.get_group(('yes', 'male', 'young', 'teacher'))
except KeyError as e:
    print(f"报错:{e}")

输出:

报错:('yes', 'male', 'young', 'teacher')

解决方案:筛选有效分组组合再处理

我们可以先获取数据中实际存在的分组键,再和目标组合做交集,只对存在的组合进行操作:

步骤1:定义目标组合列表

# 目标组合:包含存在的和不存在的
target_groups = [
    ('yes', 'male', 'young', 'student'),  # 数据中存在的组合
    ('yes', 'male', 'young', 'teacher'),  # 数据中不存在的组合
    ('no', 'female', 'old', 'engineer')   # 数据中存在的组合
]

步骤2:筛选出数据中存在的组合

grouped = df.groupby(['married', 'gender', 'age_group', 'occupation'])
# 获取所有已存在的分组键集合
existing_groups = set(grouped.groups.keys())
# 筛选出目标中实际存在的组合
valid_targets = [g for g in target_groups if g in existing_groups]

步骤3:提取有效组合的最高评分记录

用nlargest获取每组评分最高的第一条记录,再拼接结果:

# 获取有效组合的最高评分记录
result = pd.concat([grouped.get_group(g).nlargest(1, 'rating') for g in valid_targets])
print(result)

输出:

married  gender age_group occupation  views  rating
0     yes    male     young    student    150     4.2
5      no  female       old   engineer    280     4.6

进阶:保留目标组合结构(含空值)

如果需要保留所有目标组合的结构,不存在的组合用NaN填充,可以用reindex实现:

# 先获取每个分组的最高评分
grouped_rating = grouped['rating'].max().reset_index()
# 用目标组合重新索引,不存在的组合自动填充NaN
final_result = grouped_rating.set_index(['married', 'gender', 'age_group', 'occupation'])\
                             .reindex(target_groups)\
                             .reset_index()
print(final_result)

输出:

married  gender age_group occupation  rating
0     yes    male     young    student     4.2
1     yes    male     young    teacher     NaN
2      no  female       old   engineer     4.6

内容的提问来源于stack exchange,提问作者pylearner

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 07:34:01