用 Pandas 模拟 Excel 个 AverageIF

Emulate Excel AverageIFs with Pandas

我正在尝试在某个日期范围内在 Pandas 中模拟 Excel 的 AVERAGEIFs 函数,但到目前为止还没有成功。我知道我需要使用 apply 和 groupby,但显然我的语法不正确,因为我收到此错误:

TypeError: can only concatenate list (not "Timedelta") to list

我目前正在使用测试数据,试图找出语法,数据如下:

对于每个 'Avg' 列,我试图 return 前 180 天的平均数量,按 'A' 和 'B' 分组。因此,我希望第 1 行中的 'Avg' 列为 1.5((1+2)/2,同时省略第 5 行,这是一个匹配项,但已超过 180 天)。

这是我目前的代码,它不起作用: 将 pandas 导入为 pd

#Importing the dataset
df = pd.read_excel('Test.xlsx', sheet_name='Sheet1')

df = pd.concat([df, pd.DataFrame(columns=['Avg Qty'])], axis=1)
df['Avg Qty'] = df.apply(df.groupby([(['Date'] <= (['Date']+pd.Timedelta(-1, 
    unit='d')) >= (['Date']+pd.Timedelta(-180, unit='d'))), 'A', 'B']))['Qty'].mean()

print(df.head)

如有任何帮助,我们将不胜感激。

IIUC,我想你想要这样的东西:

df['Avg Qty'] = (df.groupby([pd.Grouper(freq='180D', key='Date'),'A','B'])['Qty']
                   .transform('mean'))

输出:

        Date       A         B  Qty  Cost  Avg Qty
0 2017-12-11  Cancer      Golf    1   100      1.5
1 2017-11-11  Cancer      Golf    2   200      1.5
2 2017-11-11  Cardio      Golf    2   300      2.0
3 2017-10-11  Cardio  Baseball    3   600      3.0
4 2017-04-11  Cancer      Golf    4   150      4.0
5 2016-01-01  Cancer  Football    5   200      5.0

编辑:

df = df.set_index('Date')
df.groupby(['A','B']).apply(lambda x: x.sort_index().rolling('180D')['Qty'].mean()).reset_index()\
   .merge(df.reset_index(), on=['Date','A','B'], suffixes=('_avg',''))

输出:

        A         B       Date  Qty_avg  Qty  Cost
0  Cancer  Football 2016-01-01      5.0    5   200
1  Cancer      Golf 2017-04-11      4.0    4   150
2  Cancer      Golf 2017-11-11      2.0    2   200
3  Cancer      Golf 2017-12-11      1.5    1   100
4  Cardio  Baseball 2017-10-11      3.0    3   600
5  Cardio      Golf 2017-11-11      2.0    2   300