如何为pandas rolling-apply滚动计算结果新增校验列
实现方案
你现在用的rolling.apply默认只传入窗口内的数值,拿不到对应索引的日期,不用改原有计算逻辑,按下面的代码写就能拿到所有需要的校验字段:
- 第一步先把索引转成标准datetime格式,不然时间滚动窗口容易算错:
import pandas as pd daily_data.index = pd.to_datetime(daily_data.index)
- 注意你的数据集是按日期降序排的(最新日期在最上面,越往下日期越早),和pandas默认的时间排序方向相反,我们保留这个排序,保证和你之前的计算结果完全对齐,先把日期存成普通列方便滚动取数:
daily_data['tmp_date'] = daily_data.index win_str = '180 D' close_roller = daily_data['Close'].rolling(win_str)
- 接下来聚合算收益率、首尾收盘价,再补全两个日期字段:
dfSeries = close_roller.agg( pct_change = lambda x: (x.iloc[0] - x.iloc[-1])/x.iloc[0], # 和你原来的计算逻辑完全一致 x0_close = lambda x: x.iloc[0], # 窗口第一个值,就是当前行的收盘价 x1_close = lambda x: x.iloc[-1] # 窗口最后一个值,就是180天窗口内最早那天的收盘价 ) # 补日期字段 dfSeries['x0_date'] = dfSeries.index # 就是当前行的日期,和你之前的判断一致 dfSeries['x1_date'] = daily_data['tmp_date'].rolling(win_str).apply(lambda x: x.iloc[-1]) # 把x1_date转成标准时间格式 dfSeries['x1_date'] = pd.to_datetime(dfSeries['x1_date'], unit='ns')
校验提示
你可以随便抽一行验证,比如之前输出里2022-05-26的pct_change是0.033152,对应x0_close是143.779999,用(x0_close - x1_close)/x0_close算出来的结果会和原值完全一致。
如果后续你把数据集改成常规的日期升序(早的日期在前,新的在后),只要把代码里所有iloc[0]和iloc[-1]互换就行,逻辑不用改。
内容的提问来源于stack exchange,提问作者Ivan
相关产品推荐
相关产品推荐

