文章来源:FPGA入门到精通
一、什么是滑动平均滤波器?
滑动平均滤波器(Moving Average Filter, MAF)是数字信号处理中最经典的FIR滤波器之一,通过计算窗口内数据的平均值实现噪声抑制。
输出 y[n] = 窗口内N个输入的算术平均。
计算公式:
例如第8采样点窗口大小为5的平均值滤波:
Y[8] = ( X[8] + X[9] + X[10] + X[11] + X[12] )/5
平均滤波有时间延迟,可能会出现零点偏移,为了消除这个影响,一般以当前点为中点,左右各N/2点进行移动平均。
Y[8] = ( X[6] + X[7] + X[8] + X[9] + X[10] )/5
二、时域计算方法分析
滑动平均计算虽然看似简单,只有加法和除法,但是却是十分耗时,特别是窗口特别大的时候格外明显。
Y[M] = 1/N * ( X[1]+X[2]+X3[3] + … X[N-1] )。
窗口内数据求和,可以发现一个规律,当前时刻窗口内的数据与上一个时刻窗口内的数据,只有2个值不同,所以可以看成累加求和,丢掉上一个窗口内最早的点,加上新加入的点。
Y[8] = ( X[6] + X[7] + X[8] + X[9] + X[10] )/5
Y[9] = ( X[7] + X[8] + X[9] + X[10] + X[11] )/5
可以看成:
Y[9] = Y[8] - X[6]/5 + X[11]/5
三、频率特性
移动平均值滤波也是低通滤波器的一种,其核心优势在于:
1. 低计算复杂度
无需复杂乘加运算,适合嵌入式/FPGA实时处理;
2. 零相位失真
线性相位特性保留信号时序特征;
3. 灵活可调
窗口长度N直接控制截止频率。
四、Verilog实现
以完成128点滑动平均滤波器的设计为例
这里有一个技巧,因为输入数据是一个个数据串行输入,所以只需累加输入数据的值,同时减去前面第128个数据即可。
// 128级寄存器移位缓存数据
reg [11:0] din_reg [127:0];
integer i;
always @ (posedge clk or posedge rst) begin
if (rst) begin
for (i=0; i<=255; i=i+1)
din_reg[i] <= 'd0;
end else begin
din_reg[0] <= din;
for (i=0; i<127; i=i+1)
din_reg[i+1] <= din_reg[i];
end
end
// 累加求和
reg [18:0] sum;
always @ (posedge clk or posedge rst) begin
if (rst)
sum <= 'd0;
else
sum <= sum + {{7{din[11]}},din}
- {{7{din_reg[127][11]}},din_reg[127]};
end
//求均值,右移7bit等效为÷128
assign mean = sum[18:7];