如何通过2x2平均内核对pandas数据帧进行下采样

gc5*_*gc5 5 python filtering downsampling dataframe pandas

我正在尝试对pandas数据帧进行下采样以减少粒度.在示例中,我想减少此数据帧:

1  2  3  4
2  4  3  3
2  2  1  3
3  1  3  2
Run Code Online (Sandbox Code Playgroud)

对此(下采样以使用均值获得2x2数据帧):

2.25  3.25
2     2.25
Run Code Online (Sandbox Code Playgroud)

是否有内置的方式或有效的方法来做它或我必须自己写?

谢谢

And*_*den 7

一种选择是使用groupby两次.一次为索引:

In [11]: df.groupby(lambda x: x/2).mean()
Out[11]:
     0    1  2    3
0  1.5  3.0  3  3.5
1  2.5  1.5  2  2.5
Run Code Online (Sandbox Code Playgroud)

一次为列:

In [12]: df.groupby(lambda x: x/2).mean().groupby(lambda y: y/2, axis=1).mean()
Out[12]:
      0     1
0  2.25  3.25
1  2.00  2.25
Run Code Online (Sandbox Code Playgroud)

注意:一个只能计算一次平均值的解决方案可能更可取...一个选项是stack,groupby,mean和unstack,但atm这个有点繁琐.

这似乎比Vicktor的解决方案快得多:

In [21]: df = pd.DataFrame(np.random.randn(100, 100))

In [22]: %timeit df.groupby(lambda x: x/2).mean().groupby(lambda y: y/2, axis=1).mean()
1000 loops, best of 3: 1.64 ms per loop

In [23]: %timeit viktor()
1 loops, best of 3: 822 ms per loop
Run Code Online (Sandbox Code Playgroud)

事实上,Viktor的解决方案使我的(动力不足)笔记本电脑崩溃了更大的DataFrames:

In [31]: df = pd.DataFrame(np.random.randn(1000, 1000))

In [32]: %timeit df.groupby(lambda x: x/2).mean().groupby(lambda y: y/2, axis=1).mean()
10 loops, best of 3: 42.9 ms per loop

In [33]: %timeit viktor()
# crashes
Run Code Online (Sandbox Code Playgroud)

正如Viktor所指出的,这不适用于非整数索引,如果需要,您可以将它们存储为临时变量并在以下情况下反馈它们:

df_index, df_cols, df.index, df.columns = df.index, df.columns, np.arange(len(df.index)), np.arange(len(df.columns))
res = df.groupby(...
res.index, res.columns = df_index[::2], df_cols[::2]
Run Code Online (Sandbox Code Playgroud)