【发布时间】:2022-01-20 16:36:04
【问题描述】:
This answer 提供了一种解决方案,可以根据日期窗口获取由另一列分组的列的滚动总和。在这里复制它:
df = pd.DataFrame(
{
'ID': {0: 10001, 1: 10001, 2: 10001, 3: 10001, 4: 10002, 5: 10002, 6: 10002},
'Date': {
0: datetime.datetime(2019, 7, 1),
1: datetime.datetime(2019, 5, 1),
2: datetime.datetime(2019, 6, 25),
3: datetime.datetime(2019, 5, 27),
4: datetime.datetime(2019, 6, 29),
5: datetime.datetime(2019, 7, 18),
6: datetime.datetime(2019, 7, 15)
},
'Amount': {0: 50, 1: 15, 2: 10, 3: 20, 4: 25, 5: 35, 6: 40},
}
)
amounts = df.groupby(["ID"]).apply(lambda g: g.sort_values('Date').rolling('28d', on='Date').sum())
df['amount_4wk_rolling'] = df["Date"].map(amounts.set_index('Date')['Amount'])
输出:
+-------+------------+--------+--------------------+
| ID | Date | Amount | amount_4wk_rolling |
+-------+------------+--------+--------------------+
| 10001 | 01/07/2019 | 50 | 60 |
| 10001 | 01/05/2019 | 15 | 15 |
| 10001 | 25/06/2019 | 10 | 10 |
| 10001 | 27/05/2019 | 20 | 35 |
| 10002 | 29/06/2019 | 25 | 25 |
| 10002 | 18/07/2019 | 35 | 100 |
| 10002 | 15/07/2019 | 40 | 65 |
+-------+------------+--------+--------------------+
但是,如果其中两个日期相同,则会出现错误:
pandas.errors.InvalidIndexError: Reindexing only valid with uniquely valued Index objects
这是有道理的,正如我在最后一行看到的那样,Date 被用来设置一个现在不再唯一的索引。但是,由于我不太明白最后一行是做什么的,所以我很难尝试开发替代解决方案。
有人可以帮忙吗?
【问题讨论】:
-
最后一行使用
amounts数据框作为伪字典在“Amount”列中查找值并填充“amount_4wk_rolling”列 -
我认为我的answer here 应该可以工作。您只需要聚合总和而不是平均值。 (并确保在进行聚合之前
sort_values) -
那么你想得到什么答案?如果您想在滚动中对同一天的值进行分组然后有一个值或者仍然进行滚动求和,其中同一天的不同行会有不同的总和,这是不明确的
-
@ALollz - 谢谢。所以我试过
df['amount_4wk_rolling'] = df.reset_index().groupby(["ID"]).apply(lambda g: g.sort_values('Date').rolling("28d", on="Date").agg({'Amount': 'sum', 'index': 'max'}).reset_index(drop=True).set_index('index')),但我得到了错误;ValueError: cannot handle a non-unique multi-index!。仔细检查后,代码似乎返回了一个多索引数据帧而不是一个系列,所以我已经很好地和真正地翘起。我只是想在这个阶段重新创建没有重复日期的确切答案。 -
我也试过
df['amount_4wk_rolling'] = df.sort_values('Date').reset_index().groupby(["ID"]).rolling("28d", on="Date").agg({'Amount': 'sum', 'index': 'max'}).reset_index(drop=True).set_index('index'),但后来我得到ValueError: cannot reindex from a duplicate axis