Pregunta

I just wrote the implementation of dft. Here is my code:

        int T = 2205;

        float[] sign = new float[T]; 
        for (int i = 0, j = 0; i < T; i++, j++)
            sign[i] = (float)Math.Sin(2.0f * Math.PI * 120.0f * i/ 44100.0f);

        float[] re = new float[T];
        float[] im = new float[T];
        float[] dft = new float[T];

        for (int k = 0; k < T; k++)
        {
            for (int n = 0; n < T; n++)
            {
                re[k] += sign[n] * (float)Math.Cos(2.0f* Math.PI * k * n / T);
                im[k] += sign[n] * (float)Math.Sin(2.0f* Math.PI * k * n / T);;
            }
            dft[k] = (float)Math.Sqrt(re[k] * re[k] + im[k] * im[k]);
        }

So the sampling freguency is 44100 Hz and I have a 50ms segment of a 120Hz sinus wave. According to the result I have a peak of the dft function at pont 7 and 2200. Did I do something wrong and if not, how should I interpret the results?


I tried the FFT method of AFORGE. Heres is my code.

      int T = 2048;

        float[] sign = new float[T];
        AForge.Math.Complex[] input = new AForge.Math.Complex[T];
        for (int i = 0; i < T; i++)
        {
            sign[i] = (float)Math.Sin(2.0f * Math.PI * 125.0f * i / 44100.0f);
            input[i].Re = sign[i];
            input[i].Im = 0.0;
        }

        AForge.Math.FourierTransform.FFT(input, AForge.Math.FourierTransform.Direction.Forward);
        AForge.Math.FourierTransform.FFT(input, AForge.Math.FourierTransform.Direction.Backward);

I had expected to get the original sign but I got something different (a function with only positive values). Is that normal? Thanks in advance!

¿Fue útil?

Solución

Your code look correct, but it could be more efficient, DFT is often solved by FFT algorithm (fast-fourier transform, it's not a new transform, it's just an algorithm to solve DFT in more efficient way).

Even if you do not want to implement FFT (which is a bit harder to understand and it's harder to make it work on data which is not in form of 2^n) or use some open source code, you can make your implementation a bit fast, for example by seeing that 2.0f * Math.PI * K / T is a constant outside of inner loop, so you can compute it once for each k (move it outside inner loop) and then just multiply it by n in your cos/sin functions.

As for position and interpretation, you have changed your domain, now your X-axis, which is the index of data in table corresponds not to time but frequency. You have sampling of 44100Hz and you have captures 2205 samples, that means that every 1 sample represents a magnitude of your input signal at frequency equal to 44100Hz / 2205 = 20Hz. You have your magnitude peak at 7th point (index 6) because your signal is 120Hz, so 6 * 20Hz = 120Hz which is what you could expect.

Seconds peak might seem to represent some high frequency, but it's just a spurious signal, because your sampling rate is 44100Hz you can not measure frequencies higher than 44100Hz / 2 (Nyquist's law) which if you cut-off point, after that frequency DFT data is not valid. That's why, second half of your table is invalid and it's basically your first half but mirrored and you can ignore it.

Edit// From your questions I can see that you are interested in audio processing, you might want to google NForge.Net library, which is a great opensource library for audio and visual processing and its author have many good articles on codeproject.com regarding many of it's features.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top