如何在 python 中按周滚动汇总数据?

How to do a rolling aggregation of data week wise in python?

我有一个数据集,其结构是:日期 利润

数据集的样本是:

   Date     Profit
2013-06-21   14
2013-06-22   19
2013-06-23   11
2013-06-24   13
2013-06-25   6
2013-06-26   22
2013-06-27   22
2013-06-28   3
2013-06-29   5
2013-06-30   10
2013-07-01   17
2013-07-02   14
2013-07-03   9
2013-07-04   7

Sample input 是:

data = [('2013-06-21',14),
    ('2013-06-22',19),
    ('2013-06-23',11),
    ('2013-06-24',13),
    ('2013-06-25',6),
    ('2013-06-26',22),
    ('2013-06-27',22),
    ('2013-06-28',3),
    ('2013-06-29',5),
    ('2013-06-30',10),
    ('2013-07-01',17),
    ('2013-07-02',14),
    ('2013-07-03',9),
    ('2013-07-04',7)]

现在我想做一个 rolling aggregation 并存储聚合。通过滚动聚合我的意思是说第 1 周(2013-06-21 到 2013-06-27)我想添加前一个日期的利润并将其与当前日期一起存储。所以对于 2013-06-21 总和将是 14 只是因为它是一周的第一天但是对于 2013-06-22 它应该是 previous date (2013-06-21)current date (2013-06-22) 的总和和这个应与当前日期一起存储。这将持续到本周末,然后下周将再次开始,新一周没有之前的日期。所以第一周 sample output 应该是这样的:

 Date     Profit
2013-06-21   14
2013-06-22   33  #(14 + 19)
2013-06-23   44  #(33 + 11)
2013-06-24   57  #(44 + 13) 
2013-06-25   63  #(57 + 6)
2013-06-26   85  #(63 + 22)
2013-06-27   107 #(85 + 22)

我试着查看 defaultdict 并这样做了:

def aggregate(data, key, value, func):
    measures_dict = collections.defaultdict(list)
    for k,v in zip(data[key], data[value]):
        measures_dict[k].append(v)

return [(k,func(measures_dict[k])) for k in measures_dict.keys()] 

但我没有得到结果,我认为 defaultdict 不是正确的方法。我也查看了 pandas 但我无法找到开始执行此操作的方法。谁能帮我做这个滚动聚合?

看到这个答案: Cumulative sum and percentage on column?

还有这个: http://pandas.pydata.org/pandas-docs/stable/basics.html#basics-dt-accessors 还有这个: http://pandas.pydata.org/pandas-docs/stable/groupby.html

每周累计更新:

df = pd.DataFrame(data)
df.columns = ['Date','Profit']
df['Date'] = pd.to_datetime(df['Date'])
df['weekofyear'] = df['Date'].dt.weekofyear
df.reset_index('Date')
df.sort_index(inplace=True)
df['Weekly_Cum'] = df.groupby('weekofyear').cumsum()

输出:

         Date  Profit  weekofyear  Weekly_Cum
0  2013-06-21      14          25          14
1  2013-06-22      19          25          33
2  2013-06-23      11          25          44
3  2013-06-24      13          26          13
4  2013-06-25       6          26          19
5  2013-06-26      22          26          41
6  2013-06-27      22          26          63
7  2013-06-28       3          26          66
8  2013-06-29       5          26          71
9  2013-06-30      10          26          81
10 2013-07-01      17          27          17
11 2013-07-02      14          27          31
12 2013-07-03       9          27          40
13 2013-07-04       7          27          47

@liam-foley 回答中的一个小修复:

df['year'] = df.index.year
df['weekofyear'] = df.index.weekofyear
df['Weekly_Cum'] = df.groupby(['year', 'weekofyear']).cumsum()

否则,cumsum 将计算索引中所有年份的同一工作日。