Audio filter and equalizers ed
Problems with a naive equalizer ed
- Task
- You want to change the volume of an audio signal, but only within a certain frequency range. All other frequencies should stay untouched.
Naive idea ed
This already screams to be solved via Fast Fourier Transforms (FFT) - the signal (an array of real numbers) is transformed into the frequency domain, i.e. you get a new array of complex numbers, where each entry represents the intensity (and phase information) for a specific frequency inside the original signal.
It is then trivial to scale all entries inside the desired frequency range up or down and then transforming the signal back into its time domain.
Problem ed
Yes, this works perfectly when applied to the whole audio array at once (e.g. the whole 5 min song).
But what if you want a more flexible "live" audio effect. Then the signal comes in smaller chunks, let's say 1024 numbers at a time. If you simply try to apply the naive equalizer to each chunk separately, the result will have stutter, because each chunk still gives a smooth signal, but the end of one chunk might not fit to the start of the next.
There might be fixed using additional "smoothening" afterwards to make chunks fit together. But this further degrades the signal and and increases complexity.
Filter ed
Actually, we can do without expensive FFTs...
Basic idea ed
What happens, when taking the mean of neighbouring signal values? Smoothing! - For a low frequency signal, almost nothing changes. But a high frequency signal looses intensity by self-cancellation.
The most extreme cancellation happens for a sine wave at half the sampling rate, when one value is a high peak, and the next value is a low peak, etc.
- Crappy low-pass filter
- Slightly better low-pass filter
Note, that this does not perfectly mute all frequencies above \(\omega\). Rather, there is a smooth transition around \(\omega\).
- High-pass filter
General filter ed
By linearly mixing inputs and previous outputs, we can define\begin{align}y_i &= \alpha_0 \, x_i + \alpha_1 \, x_{i-1} + \alpha_2 \, x_{i-2} + \dots - \beta_1 \, y_{i-1} - \beta_2 \, y_{i-2} - \dots \\&= \sum_{k=0}^{M} \alpha_k \, x_{i-k} - \sum_{k=1}^{N} \, \beta_k y_{i-k}\end{align}