求助:使用PartitionBy按ID计算平均销售额的问题
解决按ID去重计算平均销售额的问题
数据背景
- 部分ID对应多个
sub_segment_1(如ID=2036013106) - 部分ID对应一个
sub_segment_1和多个sub_segment_2(如ID=2035867480) - 原始数据样例:

需求
解决销售额膨胀问题,按ID计算平均销售额,公式为:销售额 / ID计数,期望结果样例:
错误尝试
使用窗口函数计算平均,但结果不符合预期:
df_u = df_u.withColumn("sales", F.avg("sales").over(Window.partitionBy("id")))
正确方案
你用窗口函数得到的是ID下所有行sales的平均值,但这和需求的「销售额/ID计数」逻辑不符——核心是同一个ID的销售额被重复统计了,需要先去重再分摊。
方法1:假设同一ID的销售额唯一
如果每个ID对应的sales值是唯一的,直接按ID聚合计算:
# 按ID分组,获取唯一销售额和该ID的行数 agg_df = df_u.groupBy("id").agg( F.first("sales").alias("total_sales"), F.count("*").alias("id_count") ) # 计算分摊后的销售额 agg_df = agg_df.withColumn("adjusted_sales", F.col("total_sales") / F.col("id_count")) # 若需保留原表其他字段,关联回去 result_df = df_u.join(agg_df.select("id", "adjusted_sales"), on="id", how="left")
方法2:同一ID可能存在不同销售额(需先去重)
如果ID对应sales有重复或不同值,先对ID和sales去重再计算:
# 去重,确保每个ID对应唯一的销售额记录 dedup_df = df_u.dropDuplicates(["id", "sales"]) # 按ID聚合计算分摊值 agg_df = dedup_df.groupBy("id").agg( F.first("sales").alias("total_sales"), F.count("*").alias("id_count") ).withColumn("adjusted_sales", F.col("total_sales") / F.col("id_count"))
内容的提问来源于stack exchange,提问作者Arun Mohan
相关产品推荐
相关产品推荐

