2
$\begingroup$

I have a functioning DTMF program. It takes a larger signal and breaks it up into many small components, then analyzes each segment with an FFT to determine if the magnitude of the response for a particular "bin", corresponding to a specific frequency, is present, thereby indicating that the number which is respresented by that frequency has been pressed, straight forward enough, but I want to implement the Goertzel Algorithm of the library jmathstudio and I can't quite figure out how to go about searching for the frequency I want. the documentation says this: enter image description here

I construct the bins like this, the term '200' is dictated by the fact that my FFT is currently of size 400, and 2000 is determined by the fact that the sample rate is 4000.

int sixNineSeven = (int)(697.0*200/2000);
int sevenSevenZero = (int)(770.0*200/2000);
int eightFiveTwo = (int)(852.0*200/2000);
int nineFourOne = (int)(941.0*200/2000);

int twelveZeroNine = (int)(1209.0*200/2000);
int thirteenThirtySix = (int)(1336.0*200/2000);
int fourteenSeventySeven = (int)(1477.0*200/2000);

I guess the main thing I need to do is this step:

Normalized frequency in the range [0,1)

But does that mean that I can totally ignore the sample frequency?

I suppose I would be doing this Geortzel operation in lieu of an FFT, so should I just search for this normalized frequency in each of the small segments?

But when I do this:

   Complex coeff = su.goertzelFrequencyAnalysis(new Vector(c), (float)(1/697));

   System.out.println("coeff "+coeff);

My output is just a bunch of garbage like this:

   coeff org.JMathStudio.DataStructure.Complex@5e228a02
   coeff org.JMathStudio.DataStructure.Complex@7bd63e39
   coeff org.JMathStudio.DataStructure.Complex@2e8f4fb3
   coeff org.JMathStudio.DataStructure.Complex@42b988a6
$\endgroup$

1 Answer 1

3
$\begingroup$

The normalized frequency '1' corresponds to the Nyquist frequency, i.e. half the sampling frequency. So the normalized frequencies $w$ are obtained from the frequencies $f$ in Hz by

$$w=\frac{2f}{f_s}$$

where $f_s$ is the sampling frequency.

The frequency (in Hz) corresponding to a certain bin $i$ ($0\le i\le N-1$) of an FFT with length $N$ is

$$f_i=\frac{if_s}{N}\quad i=0,1,\ldots,N-1$$

For real-valued signals, the bins $i=N/2+1$ (assuming $N$ is even) to $i=N-1$ are redundant.

$\endgroup$
12
  • $\begingroup$ in determining those bins, why is it necessary to use half the sampling frequency and half the total size of the fourier transform? $\endgroup$
    – user8769
    Commented May 4, 2014 at 9:14
  • 1
    $\begingroup$ @matthias.anglicus: Because if the signal is real-valued, the other bins are redundant. The spectrum of a real-valued signal is conjugate symmetrical. $\endgroup$
    – Matt L.
    Commented May 4, 2014 at 9:28
  • $\begingroup$ int nineFourOne = (int)(941.0*200/2000); so for that one, to find the bin that represents the frequency of 941, we must multiply it by 200 if we've taken a fourier transform of 400 points and divide it by 2000 if the sampling rate is 4000? $\endgroup$
    – user8769
    Commented May 4, 2014 at 9:34
  • $\begingroup$ and we do that becasue of the symertrical property of the FFT transform? $\endgroup$
    – user8769
    Commented May 4, 2014 at 9:34
  • $\begingroup$ There a two things: the symmetry of the FFT, and the sampling theorem which says that in a sampled signal there cannot be any frequencies greater than half the sampling frequency. If you number the FFT-bins from $i=0$ to $i=N-1$, where $N$ is the FFT length, the index corresponding to a frequency $f_i$ is given by $i=Nf_i/f_s$, where $f_s$ is the sampling frequency. And all information is contained in the indices $0\le i\le N/2$. $\endgroup$
    – Matt L.
    Commented May 4, 2014 at 9:42

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.