Comments on Moving average that uses less memory?
Parent
Moving average that uses less memory?
My control system gets a signal representing the plant output, but that signal has a lot of noise on it. The control system goes nuts trying to react to the noise. I need to filter out the noise somehow, but preserve the basic plant response. I heard about a moving average and tried it. It helps, but uses up a lot of memory in my small microcontroller. It also introduces some lag.
Is there a way to get rid of the noise, use less memory, and maybe have less lag too?
Post
I'm adding this as a corollary to Olin's post, in case an exact formula for attenuation is needed.
That basic IIR is derived from the exponential moving average, and its impulse response is:
$$h[n]=\alpha x[n]+(1-\alpha)x[n-1]$$
which translates into this transfer function:
$$H(z)=\frac{\alpha}{1-(1-\alpha)z^{-1}}$$
This can be used to determine analytically the attenuation at a particular frequency, by simply substituting $z^{-1}=\text{e}^{-j\Omega}$:
\begin{align*} H(j\Omega)=\frac{\alpha}{1-(1-\alpha)\text{e}^{-j\Omega}} \\ |H(j\Omega)|=\frac{\alpha}{\sqrt{2(\alpha-1)(\cos(\Omega)-1)+\alpha^2)}}\tag{1} \end{align*}
The -3 dB point can also be calculated from $(1)$:
\begin{align*}|H(\Omega)|^2=\frac12=\frac{\alpha^2}{2(\alpha-1)(\cos(\Omega)-1)+\alpha^2}\quad\Rightarrow \\ 2(\alpha-1)(\cos(\Omega)-1)+\alpha^2=2\alpha^2\quad\Rightarrow \\ \cos(\Omega)-1=\frac{\alpha^2}{2(\alpha-1)}\quad\Rightarrow \\ \Omega=\arccos\left(1+\frac{\alpha^2}{2(\alpha-1)}\right)\end{align*}
This can be easily tested with any simulator. As an example, for $\alpha=0.4$, the attenuation at $0.37\frac{f_s}{2}$ and the -3 dB point are:
\begin{align*} |H(0.37\pi)|=\frac{0.4}{\sqrt(2(0.4-1)(\cos(0.37\pi)-1)+0.4^2)}=0.4255746548210215 \\ f=\frac{1}{\pi}\arccos\left(\frac{0.4^2}{2(0.4-1)}+1\right)=0.1662579714811903 \end{align*}
(where I used a normalized [0...Nyquist])
0 comment threads