有一种方法可以在没有任何额外技巧的情况下做到这一点,但它需要您有一个排序维度。与大多数时间序列数据一样,您应该可以使用时间变量。那么解决方法就很简单了:
- 倒序排列
- 使用标准的
.rolling(window) 功能
- (可选)再次排序
示例:睡眠研究
from pydataset import data
sleep_study = data('sleepstudy')
print(sleep_study.head(5))
Reaction Days Subject
1 249.5600 0 308
2 258.7047 1 308
3 250.8006 2 308
4 321.4398 3 308
5 356.8519 4 308
1) 向后排序
sleep_study.sort_values(by=['Subject', 'Days'], ascending=False, inplace=True)
2) 使用.rolling(window)
assert sleep_study.index.is_unique
sleep_study['max_react_next_3_days'] = sleep_study\
.groupby(['Subject'], as_index=False)['Reaction']\
.rolling(window=3, min_periods=1, closed='left').max()['Reaction']
sleep_study['expected_output'] = sleep_study['max_react_next_3_days'] > 400
解释:
- 我们想提前 3 天看,因此
window=3
- 但是,研究只剩下 2 或 1 天也可以,所以
min_periods=1 -- 这取决于您的假设/喜好
- 我们要使用下一个 3 天,而不是当天,所以我们使用
closed='left' 排除它,这意味着rolling 需要一个半开间隔,即开在“右”,“左”闭。
-
警告:您的数据集必须具有唯一索引才能使此代码正常工作,否则会出现静默错误
3) 再次排序,这样就没有惊喜了
sleep_study.sort_values(by=['Subject', 'Days'], ascending=True, inplace=True)
结果:
print(sleep_study.head(20))
Reaction Days Subject max_react_next_3_days expected_output
1 249.5600 0 308 321.4398 False
2 258.7047 1 308 356.8519 False
3 250.8006 2 308 414.6901 True
4 321.4398 3 308 414.6901 True
5 356.8519 4 308 414.6901 True
6 414.6901 5 308 430.5853 True
7 382.2038 6 308 466.3535 True
8 290.1486 7 308 466.3535 True
9 430.5853 8 308 466.3535 True
10 466.3535 9 308 NaN False
11 222.7339 0 309 205.2658 False
12 205.2658 1 309 207.7161 False
13 202.9778 2 309 215.9618 False
14 204.7070 3 309 215.9618 False
15 207.7161 4 309 217.7272 False
16 215.9618 5 309 224.2957 False
17 213.6303 6 309 237.3142 False
18 217.7272 7 309 237.3142 False
19 224.2957 8 309 237.3142 False
20 237.3142 9 309 NaN False