Pregunta

I am trying to write a small Discrete Fourier Transformation in Java to find the magnitude spectrum in a clear 400 Hz Sinus Signal (1 second as pcm signed-short)

So first I calculate the DFT for the complex values:

public void berechneDFT(int abtastwerte) {
        int i;

        int N = abtastwerte;
        ReX = new double[N/2+1];
        ImX = new double[N/2+1];

        TextFileOperator tfo = new TextFileOperator(file.substring(0, file.length()-4)+"_DFT.txt");

        try {
            tfo.openOutputStream();
            tfo.writeString("ReX      ImX\n");
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }

        // real-Anteil berechnen
        for (i=0, ReX[i] = 0, ImX[i] = 0; i <= N/2; i++)
        {
            for(int n=0; n < N; n++)
            {
                ReX[i] += x[n] * Math.cos( (2.0 * Math.PI * n * i) / (double) N);
                ImX[i] += - (x[n] * Math.sin( (2.0 * Math.PI * n * i) / (double) N));
            }

            tfo.writeString(ReX[i] +" "+ImX[i]+"\n");
        }

        x = null;   
        tfo.closeOutputStream();    // flush

        System.out.println("Anteile berechnet.");
    }

And then I try to calculate the magnitude Spectrum:

public void berechneBetragsSpektrum() {

        int N = ReX.length;

        TextFileOperator tfo = new TextFileOperator("betragsspektrum_400hz.txt");
        try {
            tfo.openOutputStream();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }
        double powerAtFreq;
        int marker = 0;
        double maxPowerAtFreq = 0;

        for(int i=0; i < N; i++)
        {
            double A1 = ReX[i] * ReX[i];
            double A2 = ImX[i] * ImX[i];

            powerAtFreq = Math.sqrt(A1+A2);

            if(powerAtFreq > maxPowerAtFreq)
            {
                maxPowerAtFreq = powerAtFreq;
                marker = i;
            }

            tfo.writeString(powerAtFreq+"\n");
        }

        tfo.closeOutputStream();
        System.out.println("Stärkste Frequenz: "+(marker)+" Hz");
    }

But for some reason I only get the result of 400 Hz in the 'marker' if I choose to check for all 16000 samples. But shouldn't I see the peak in 400 Hz also if I only choose 800 samples, because with 800 I could see 800/2 = 400 Hz as maximum frequency?

I guess some little thing must be wrong with the code, because if I choose 800 samples I get 20 Hz, for 1600 samples I get 40 Hz which is always 1/40 * sample rate.

What the hell do I miss or did wrong? The results are strange..

Note that if I do the inverse DFT with the complex values I can reconstruct the audio signal again!

¿Fue útil?

Solución

The answer for the question is that if you calculate the fourier transforms, magnitude spectrum etc. the indices show relative frequencies which need to be calculated to their correct value.

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