如何用Groupby统计DataFrame单列分组内的组合出现次数?
解决方案
要实现按id分组统计tag列的两两组合(含自身组合)出现次数,并将结果作为新列添加到原DataFrame中,可以按以下步骤操作:
步骤说明
- 统计分组内tag的频数:先按
id分组,计算每个分组中各tag值的出现次数。 - 生成组合列名:基于所有唯一
tag值,生成所有x≤y形式的组合列名(如1,1、1,2)。 - 计算组合次数:对每个分组,根据tag频数计算各组合的出现次数:
- 当
x=y时,次数为组合数公式C(n,2) = n*(n-1)//2(即从n个相同tag中选2个的组合数) - 当
x≠y时,次数为两个tag频数的乘积count(x)*count(y)
- 当
- 合并结果到原DataFrame:将每个分组的组合统计结果关联回原DataFrame,确保同一
id的所有行都填充对应统计值。
完整代码
import pandas as pd # 初始化数据 data = { "id": ['a', 'a', 'a', 'a', 'a', 'a', 'b', 'b', 'b', 'b', 'b', 'b'], "tag": [1, 1, 2, 2, 3, 3, 2, 2, 2, 3, 3, 3]} df = pd.DataFrame(data) # 1. 按id分组统计tag的出现频数 tag_counts = df.groupby('id')['tag'].value_counts().unstack(fill_value=0) # 2. 生成所有x<=y的组合列名 all_tags = sorted(df['tag'].unique()) combinations = [f"{x},{y}" for x in all_tags for y in all_tags if x <= y] # 3. 计算每个分组的组合次数 def calculate_combination_counts(row): counts = row.to_dict() combo_values = [] for x in all_tags: for y in all_tags: if x > y: continue cnt_x = counts[x] cnt_y = counts[y] if x == y: val = cnt_x * (cnt_x - 1) // 2 else: val = cnt_x * cnt_y combo_values.append(val) return pd.Series(combo_values, index=combinations) combo_counts = tag_counts.apply(calculate_combination_counts, axis=1) # 4. 合并结果到原DataFrame result_df = df.merge(combo_counts, left_on='id', right_index=True) # 查看结果 print(result_df)
输出验证
运行代码后得到的result_df与你提供的期望输出完全一致:
- 分组
a中,1,1的次数为1(C(2,2)=1),1,2的次数为4(2*2=4) - 分组
b中,2,2的次数为3(C(3,2)=3),2,3的次数为9(3*3=9) - 不存在的tag组合(如分组
b中的1,1)填充为0
内容的提问来源于stack exchange,提问作者ManOnTheMoon
相关产品推荐
相关产品推荐

