移动平均法
一、直观理解:用邻域均值抹平瞬时抖动
移动平均(Moving Average)可以理解为:不直接相信某一个时刻的读数,而是看它附近一小段时间的平均水平。
想象你在记录某路口每分钟的车流量。某一分钟刚好赶上红灯切换,计数突然冲高;下一分钟又回到常态。如果把每一分钟都当成“真实需求”,后续模型会被这种瞬时噪声带着跑。更稳妥的做法是:取当前时刻前后若干分钟的平均,用这个局部均值代表该点附近的趋势。
这就是简单移动平均的核心思想:
- 选定窗口宽度 ;
- 对每个时刻,用窗口内观测值的算术平均替代原值;
- 窗口越大,曲线越平滑,但对突变的反应越迟钝。
移动平均不会“创造”新的物理量,它只是把高频抖动压低,把较慢的趋势或周期留下来。因此它既可用于去噪可视化,也可作为构造趋势特征的基线方法。
需要区分两种常用形式:
- 居中移动平均:窗口对称地取过去和未来,适合事后分析与绘图,不适合在线预测;
- 因果(后向)移动平均:只用当前及过去的观测,适合预测、滤波和实时监控。
二、适用场景与优缺点
| 类型 | 说明 |
|---|---|
| 适用场景 | 时间序列或等间隔采样信号存在高频噪声;需要提取日/周趋势;需要构造平滑后的解释变量;需要快速建立可复现的去噪基线。 |
| 核心优点 | 原理透明、计算简单、结果易复核;窗口含义直观,便于与业务周期对应;对中等强度随机噪声通常有效。 |
| 局限与缺点 | 会抹平真实尖峰与突变;引入相位滞后(尤其是后向平均);窗口两端边界处理不唯一;对非等间隔采样需先重采样或改用加权方案。 |
使用移动平均前通常需要完成以下检查:
- 确认序列大致等间隔,或已完成重采样;
- 明确目标是“事后看趋势”还是“在线预测/特征构造”;
- 估计噪声时间尺度与关心的信号时间尺度;
- 检查是否存在不应被抹平的尖峰、故障点或制度突变;
- 若用于监督学习,平滑参数只能在训练集上选定,并按同样规则映射到测试集。
如果序列含季节性,简单移动平均只能压噪声,不能自动分离季节项;此时应考虑季节分解、STL 或更专门的滤波方法。
三、核心原理:局部算术平均
设观测序列为 。
1. 奇数窗口的居中移动平均
取窗口宽度 ,则居中移动平均为:
例如 时,,每个点用自身及前后各 2 个点求平均。
2. 后向(因果)移动平均
预测或实时场景中不能使用未来值,应采用:
此时平滑结果相对原信号会有滞后,滞后期大约为 个采样间隔。
3. 边界处理
序列两端无法凑满完整窗口。常见做法包括:
- 缩小窗口(如 MATLAB
movmean默认在边缘使用可用点); - 端点复制或对称延拓后再平均;
- 直接将两端 个点标为缺失,不参与后续建模。
无论采用哪种规则,都应在报告中写清楚,避免复现时出现长度不一致。
4. 与加权移动平均的关系
普通移动平均对窗口内各点等权。若希望更强调近期观测,可使用指数加权移动平均(EWMA):
其中 。EWMA 仍是“局部平均”思想,只是权重随时间衰减。
四、关键决策:窗口如何选
窗口宽度是移动平均最关键的超参数。
1. 与业务周期对齐
- 若要压掉日内噪声、保留日趋势,窗口可取若干个采样点对应的“几小时”;
- 若数据是日频、希望平滑掉星期效应以外的毛刺,窗口可试 3、5、7;
- 窗口明显长于关心的变化尺度时,趋势本身也会被削平。
2. 平滑强度与信息损失的权衡
可同时观察:
- 原序列与平滑序列的残差 是否近似像高频噪声;
- 已知事件(促销、故障、政策节点)附近的峰是否被过度削平;
- 不同窗口下,后续回归/预测指标的变化。
3. 预测场景必须用因果形式
比赛或工程里若要用 时刻信息预测 ,特征中的移动平均不能偷偷用到 。居中平均只适合回顾性分析。
4. 缺失值与异常值
窗口内若存在缺失,简单平均会偏向剩余点;若存在极端异常,均值会被拉偏。更稳健时可先做异常处理,或改用移动中位数。
五、MATLAB 示例
下面用一条含噪声和尖峰的短序列,比较不同窗口与居中/后向平滑。
% 构造示例序列:缓慢趋势 + 正弦 + 噪声 + 一个尖峰
rng(1);
t = (1:40)';
y = 0.05*t + sin(2*pi*t/12) + 0.25*randn(size(t));
y(20) = y(20) + 3; % 人为尖峰,观察平滑是否过度抹平
% 窗口宽度
w = 5;
% 居中移动平均(事后分析)
yCenter = movmean(y, w); % 默认居中,边缘自动缩窗
% 后向移动平均(因果,可用于预测特征)
yCausal = movmean(y, [w-1, 0]); % 使用过去 w-1 个点与当前点
% 对照:更大窗口
yCenter9 = movmean(y, 9);
figure;
plot(t, y, "-o", "DisplayName", "原始序列");
hold on;
plot(t, yCenter, "-s", "LineWidth", 1.5, "DisplayName", "居中 MA (w=5)");
plot(t, yCausal, "-d", "LineWidth", 1.5, "DisplayName", "后向 MA (w=5)");
plot(t, yCenter9, "-", "LineWidth", 1.5, "DisplayName", "居中 MA (w=9)");
xline(20, "--", "尖峰位置");
xlabel("时间 t");
ylabel("观测值");
title("移动平均:窗口与因果性的影响");
legend("Location", "best");
grid on;
% 残差:可粗略判断“被去掉的是不是高频成分”
resid = y - yCenter;
fprintf("居中MA残差的标准差 = %.4f\n", std(resid));
fprintf("原始序列标准差 = %.4f\n", std(y));
若序列在表中,也可直接对表变量做滚动统计:
tbl = table(t, y, yCenter, yCausal, ...
"VariableNames", ["t", "y", "yCenter", "yCausal"]);
disp(tbl(1:8, :)); % 查看边缘缩窗后的前几项
六、如何解释结果
解释移动平均结果时,重点不是“曲线变好看了”,而是说明平滑改变了什么、保留了什么。
完整报告通常应包括:
- 原始采样频率与是否等间隔;
- 窗口宽度及其业务含义(对应多长时间);
- 采用居中还是后向平均,以及原因;
- 边界如何处理;
- 平滑前后关键统计量(均值、方差、峰位置)的变化;
- 是否误伤了真实事件峰;
- 平滑结果在后续模型中的角色(仅可视化 / 作为特征 / 作为标签的预处理)。
若把平滑序列送入回归或分类模型,还应比较“不平滑”与“平滑”两种输入在验证集上的表现,防止为了好看而损失预测信息。
七、常见误区
1. 在预测特征里使用居中移动平均
居中平均用了未来观测,会造成严重的数据泄漏,验证指标会虚高,线上失效。
2. 窗口拍脑袋取很大
窗口过大时,不仅噪声消失,连要研究的趋势拐点、周期峰谷也会被削平,模型学到的是过度模糊的信号。
3. 把平滑值当成原始测量上报
论文或赛题解答中若讨论测量误差、达标判定,应明确区分原始观测与滤波结果,否则量纲和不确定度都会被误解。
4. 忽略非等间隔采样
传感器掉点、交易日休市会导致时间间隔不等。此时直接对下标做 movmean,物理时间尺度是扭曲的。
5. 用同一组全样本先选窗再评估
窗口也是超参数。应在训练折内选择,再固定到验证/测试折,否则平滑强度本身会过拟合。
八、小结
移动平均的核心思想可以概括为:
用局部邻域的平均值代替单点观测,压低高频噪声,突出较慢变化的趋势。
它适合作为时间序列去噪和趋势特征的第一基线:实现简单、参数少、便于答辩解释。代价是可能滞后、可能削峰,并且窗口选择必须与任务的时间尺度和因果约束一致。
实际建模中,可先用小窗口后向移动平均建立可复现基线;若必须保留峰形与局部斜率,再考虑 Savitzky-Golay 等更专门的平滑方法。