Simple and efficient algorithm for detecting the frequency and phase of a sinusoidal signal

I need an algorithm to determine the frequency and phase of a pure sine wave. The input signal frequency ranges from 0 to 100 Hz.

The signal value is clamped at 20 kHz (which is why I get 20,000 values ​​per second) - this is set and cannot be changed. I need to determine the frequency and phase of this input signal and use PWM to generate MCU interrupts at the same frequency as the input signal.

Can anyone suggest what algorithm to use to make this simple and efficient? Maybe Goertzel's algorithm?

+3


source to share


1 answer


Goertzel's algorithm is good for detecting a given frequency (or multiple frequencies).
To find the unknown frequency of a sine wave, you can use the Fourier transform .

The peak with the largest value corresponds to the sinusoidal frequency, and the phase of these harmonics corresponds to its phase.

The phase derived from the FT result may be affected by noise. A more robust approach is to use zero phased sine wave cross-correlation (at the same frequency) to obtain the phase shift.



There are many FFT implementations in C. Fast one - fftw.org (portability to any C compiler), but I doubt you really need such a complex library for a microcontroller. Take any good Cooley-Tukey 40-line codes like this

PS If your signal is truly a perfect sine at a single frequency without significant noise, then the zero-crossing method suggested in the parallel thread would be better.

+3


source







All Articles