如何在Pandas中为各产品的折扣变动分配连续递增的promotion_id
如何为每个产品的折扣变化分配连续递增的促销ID?
看起来你需要针对每个产品,按照时间顺序追踪折扣的变化——每次折扣变动时生成一个新的递增ID,相同的连续折扣则共用同一个ID。这在Pandas里可以通过分组+差分+累计求和轻松实现,我给你详细拆解步骤:
核心思路与步骤
- 确保数据按时间和产品排序:折扣变化是基于时间线的,必须先把数据按
product_code和date排序,保证我们是按时间先后判断折扣的变动。 - 分组检测折扣变动:对每个产品组,用
diff()方法对比当前行与上一行的discount值,只要折扣发生变化就标记为一个变动点。 - 累计求和生成连续ID:把所有变动点累计求和,就能得到连续递增的
promotion_id。
代码实现
假设你的DataFrame名为df,可以这样写:
import pandas as pd # 先把字符串日期转为datetime类型,避免排序出错 df['date'] = pd.to_datetime(df['date'], format='%d/%m/%Y') # 按产品和日期排序,保证时间顺序正确 df = df.sort_values(['product_code', 'date']) # 生成promotion_id df['promotion_id'] = df.groupby('product_code')['discount'].diff().ne(0).cumsum()
代码细节解释
pd.to_datetime(...):把字符串格式的日期转换成datetime类型,避免出现"01/12/2022"和"02/01/2022"这类字符串排序错误。sort_values(...):确保每个产品的记录严格按时间先后排列,这样后续的diff()才能准确判断折扣变化。groupby('product_code')['discount'].diff():对每个产品组,计算当前行折扣与上一行的差值,每个产品的第一行会得到NaN。.ne(0):把差值不等于0的行(也就是折扣变化的行)标记为True,其余为False;NaN会被自动识别为False。.cumsum():对True/False值累计求和(True视为1,False视为0),每次折扣变化时就累加1,自然生成连续递增的ID。
结果验证
用你给出的单一产品示例测试,生成的promotion_id会和你预期完全一致:
date product_code discount promotion_id
01/01/2022 1 0.7 1
02/01/2022 1 0.1 2
02/01/2022 1 0.1 2
03/01/2022 1 0.4 3
04/01/2022 1 0.1 4
05/01/2022 1 0.1 4
06/01/2022 1 0.1 4
06/01/2022 1 0.5 5
这种方法用的是Pandas的矢量化操作,处理大规模数据也能保持高效,完全不用担心性能问题。
内容的提问来源于stack exchange,提问作者Alessandro Ceccarelli
相关产品推荐
相关产品推荐

