Main Content

Savitzky-Golay filter design

Savitzky-Golay filters are used to smooth out noisy signals with a large frequency span. Savitzky-Golay smoothing filters tend to filter out less of the signal's high-frequency content than standard averaging FIR filters. However, they are less successful at rejecting noise when noise levels are particularly high.

In general, filtering consists of replacing each point of a signal by some combination of
the signal values contained in a moving window centered at the point, on the assumption that
nearby points measure nearly the same underlying value. For example, moving average filters
replace each data point with the local average of the surrounding data points. If a given data
point has *k* points to the left and *k* points to the
right, for a total window length of *L* = 2*k* + 1, the moving average filter makes the replacement

$${x}_{s}\to {\widehat{x}}_{s}=\frac{1}{L}{\displaystyle \sum _{r=-k}^{k}{x}_{s+r}.}$$

Savitzky-Golay filters generalize this idea by least-squares fitting an
*n*th-order polynomial through the signal values in the window and taking
the calculated central point of the fitted polynomial curve as the new smoothed data point.
For a given point, *x _{s}*,

$$\left[\begin{array}{c}{x}_{s-k}\\ \vdots \\ {x}_{s-1}\\ {x}_{s}\\ {x}_{s+1}\\ \vdots \\ {x}_{s+k}\end{array}\right]=\left[\begin{array}{c}{b}_{0}+{b}_{1}\left({t}_{s}-k\Delta t\right)+{b}_{2}{\left({t}_{s}-k\Delta t\right)}^{2}+\cdots +{b}_{n}{\left({t}_{s}-k\Delta t\right)}^{n}\\ \vdots \\ {b}_{0}+{b}_{1}\left({t}_{s}-1\Delta t\right)+{b}_{2}{\left({t}_{s}-1\Delta t\right)}^{2}+\cdots +{b}_{n}{\left({t}_{s}-1\Delta t\right)}^{n}\\ {b}_{0}+{b}_{1}\left({t}_{s}-0\Delta t\right)+{b}_{2}{\left({t}_{s}-0\Delta t\right)}^{2}+\cdots +{b}_{n}{\left({t}_{s}-0\Delta t\right)}^{n}\\ {b}_{0}+{b}_{1}\left({t}_{s}+1\Delta t\right)+{b}_{2}{\left({t}_{s}+1\Delta t\right)}^{2}+\cdots +{b}_{n}{\left({t}_{s}+1\Delta t\right)}^{n}\\ \vdots \\ {b}_{0}+{b}_{1}\left({t}_{s}+k\Delta t\right)+{b}_{2}{\left({t}_{s}+k\Delta t\right)}^{2}+\cdots +{b}_{n}{\left({t}_{s}+k\Delta t\right)}^{n}\end{array}\right]=\left[\begin{array}{c}{a}_{0}+{a}_{1}\left(-k\right)+{a}_{2}{\left(-k\right)}^{2}+\cdots +{a}_{n}{\left(-k\right)}^{n}\\ \vdots \\ {a}_{0}+{a}_{1}\left(-1\right)+{a}_{2}{\left(-1\right)}^{2}+\cdots +{a}_{n}{\left(-1\right)}^{n}\\ {a}_{0}+{a}_{1}\left(0\right)+{a}_{2}{\left(0\right)}^{2}+\cdots +{a}_{n}{\left(0\right)}^{n}\\ {a}_{0}+{a}_{1}\left(1\right)+{a}_{2}{\left(1\right)}^{2}+\cdots +{a}_{n}{\left(1\right)}^{n}\\ \vdots \\ {a}_{0}+{a}_{1}\left(k\right)+{a}_{2}{\left(k\right)}^{2}+\cdots +{a}_{n}{\left(k\right)}^{n}\end{array}\right]$$

or, in terms of matrices,

$$x=\left[\begin{array}{ccccc}1& -k& {\left(-k\right)}^{2}& \cdots & {\left(-k\right)}^{n}\\ 1& \vdots & \vdots & \u22f0& \vdots \\ 1& -2& {\left(-2\right)}^{2}& \cdots & {\left(-2\right)}^{n}\\ 1& -1& {\left(-1\right)}^{2}& \cdots & {\left(-1\right)}^{n}\\ 1& 0& 0& \cdots & 0\\ 1& 1& {1}^{2}& \cdots & {1}^{n}\\ 1& 2& {2}^{2}& \cdots & {2}^{n}\\ 1& \vdots & \vdots & \ddots & \vdots \\ 1& k& {k}^{2}& \cdots & {k}^{n}\end{array}\right]\left[\begin{array}{c}{a}_{0}\\ \vdots \\ {a}_{n}\end{array}\right]\equiv Ha.$$

To find the Savitzky-Golay estimates, use the pseudoinverse of **H** to compute **a** and then premultiply by **H**:

$$\widehat{x}=H{\left({H}^{T}H\right)}^{-1}{H}^{T}x=Bx.$$

To avoid ill-conditioning, `sgolay`

uses the `qr`

function to compute an economy-size decomposition of **H** as **H** = **Q****R**, in terms of which **B** = **Q****Q**^{T}.

It is necessary to compute **B** only once. The Savitzky-Golay estimates for most signal points result from
convolving the signal with the center row of **B**. The result is the steady-state portion of the filtered signal. The first
*k* rows of **B** yield the initial transient, and the final *k* rows of **B** yield the final transient. See `sgolayfilt`

for an example. It is possible to improve noise suppression by
increasing the window length, but this introduces ringing analogous to the Gibbs phenomenon
near any transients.

[1] Orfanidis, Sophocles J.
*Introduction to Signal Processing*. Englewood Cliffs, NJ: Prentice
Hall, 1996.

[2] Press, William H., Saul A.
Teukolsky, William T. Vetterling, and Brian P. Flannery. *Numerical Recipes in C:
The Art of Scientific Computing*. New York: Cambridge University Press,
1992.

[3] Schafer, Ronald W. “What
*Is* a Savitzky-Golay Filter? [Lecture Notes].” *IEEE Signal
Processing Magazine* Vol. 28, Number 4, July 2011, pp. 111–117. https://doi.org/10.1109/MSP.2011.941097.

`filter`

| `fir1`

| `firls`

| `sgolayfilt`