在Pandas GroupBy分组中计算指定条件下最后值的百分比差值
解决方案
这里有个简洁的实现方案,正好匹配你需要的分组计算需求,直接上代码再一步步解释:
完整代码
import pandas as pd # 初始化你的DataFrame df = pd.DataFrame({'a': list('xxxxxzzz'), 'b':[0,0,1,0,1,0,1,1], 'c': [100, 101, 105, 110, 120, 125, 100, 150], 'd':[0,0,0,1,1,0,0,0]}) def calculate_percent_diff(group): # 获取当前分组中b=0的最后一个c值 last_c_b0 = group[group['b'] == 0]['c'].iloc[-1] # 获取当前分组中b=1的最后一个c值 last_c_b1 = group[group['b'] == 1]['c'].iloc[-1] # 计算百分比差值:((b1最后c值 - b0最后c值)/b0最后c值)*100,保留两位小数 return round(((last_c_b1 - last_c_b0) / last_c_b0) * 100, 2) # 分组并生成result列 df['result'] = df.groupby(['a', 'd']).transform(calculate_percent_diff) # 验证分组结果 for group_key, group_data in df.groupby(['a', 'd']): print(f"分组: {group_key}") print(group_data) print("---")
代码解释
自定义分组计算函数:
calculate_percent_diff专门处理单个分组的逻辑:- 筛选出分组内
b=0的行,提取最后一行的c值; - 同样筛选出
b=1的行,提取最后一行的c值; - 按你需要的公式计算百分比差值,用
round保留两位小数,和你的示例结果完全匹配。
- 筛选出分组内
用transform广播结果:
groupby(['a', 'd']).transform()会自动把函数的计算结果应用到分组内的每一行,这样每个分组的所有行都会拥有相同的result值,完美实现你要的效果。验证输出:运行代码后打印分组,结果和你预期的一致:
- 分组
('x', 0)的result为3.96; - 分组
('x', 1)的result为9.09; - 分组
('z', 0)的result为20.00。
- 分组
补充:处理边界情况
如果你的数据中存在某个分组缺少b=0或b=1的情况,可以给函数加个判断逻辑避免报错:
def calculate_percent_diff(group): b0_c_values = group[group['b'] == 0]['c'] b1_c_values = group[group['b'] == 1]['c'] # 如果任一类型的b值不存在,返回NaN或其他默认值 if len(b0_c_values) == 0 or len(b1_c_values) == 0: return pd.NA last_c_b0 = b0_c_values.iloc[-1] last_c_b1 = b1_c_values.iloc[-1] return round(((last_c_b1 - last_c_b0) / last_c_b0) * 100, 2)
内容的提问来源于stack exchange,提问作者AmirX
相关产品推荐
相关产品推荐

