移动平均线或移动平均线

新手上路,请多包涵

是否有用于 Python 的 SciPy 函数或 NumPy 函数或模块来计算给定特定窗口的一维数组的运行平均值?

原文由 Shejo284 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 909
2 个回答

对于一个简短、快速的解决方案,它在一个循环中完成整个事情,没有依赖关系,下面的代码效果很好。

 mylist = [1, 2, 3, 4, 5, 6, 7]
N = 3
cumsum, moving_aves = [0], []

for i, x in enumerate(mylist, 1):
    cumsum.append(cumsum[i-1] + x)
    if i>=N:
        moving_ave = (cumsum[i] - cumsum[i-N])/N
        #can do stuff with moving_ave here
        moving_aves.append(moving_ave)

原文由 Aikude 发布,翻译遵循 CC BY-SA 3.0 许可协议

更新: 已经提出了更有效的解决方案, uniform_filter1d 来自 scipy 可能是“标准”第 3 方库中最好的,一些更新的或专门的库也可用。


您可以为此使用 np.convolve

 np.convolve(x, np.ones(N)/N, mode='valid')

解释

运行平均值是 卷积 数学运算的一个例子。对于运行平均值,您沿着输入滑动一个窗口并计算窗口内容的平均值。对于离散的一维信号,卷积是一样的,除了计算任意线性组合而不是平均值,即,将每个元素乘以相应的系数并将结果相加。这些系数(窗口中的每个位置一个)有时称为卷积 _核_。 N 个值的算术平均值为 (x_1 + x_2 + ... + x_N) / N ,因此对应的内核为 (1/N, 1/N, ..., 1/N) ,这正是我们使用 np.ones(N)/N 得到的结果

边缘

mode np.convolve 指定了如何处理边缘。我在这里选择了 valid 模式,因为我认为这是大多数人期望运行平均值的方式,但您可能有其他优先事项。这是说明模式之间差异的图表:

 import numpy as np
import matplotlib.pyplot as plt
modes = ['full', 'same', 'valid']
for m in modes:
    plt.plot(np.convolve(np.ones(200), np.ones(50)/50, mode=m));
plt.axis([-10, 251, -.1, 1.1]);
plt.legend(modes, loc='lower center');
plt.show()

运行均值卷积模式

原文由 lapis 发布,翻译遵循 CC BY-SA 4.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题