/* This returns an arry of complex numbers. This is not the amplitude of the wave. It must be run through Pythagorus. */ /* DFTFunc Purpose: Forward DFT for a double array of samples of size n. This converts data in the time domain to the frequency domain. It returns a complex number array for usage in inverse DFT funcitons. To properly plot the data returned from this, data will have to be run through pythagorus. Parameters: s: Signal we are changing n: Size of the signal */ public newComplex[] DFTFunc(double[] s, int n) { newComplex[] cmplx = new newComplex[n]; double re; /*real*/ double im; /*imaginary*/ for (int f = 0; f < n - 1; f++) { re = 0; im = 0; for (int t = 0; t < n - 1; t++) { re += s[t] * Math.Cos(2 * Math.PI * t * f / n); im -= s[t] * Math.Sin(2 * Math.PI * t * f / n); } cmplx[f] = new newComplex(re, im); } return cmplx; }
/* Preforms the inverse of DFT: this will be displayed to the graph for testing with cosWavCreation */ /* invDFT Purpose: Inverse Descrete Fourier Transform, used to convert from the frequency domain to the time domain. Parameters: A: Complex array to convert n: Size of the complex array */ public double[] invDFT(newComplex[] A, int n) { double[] s = new double[n]; double re; /*real*/ double im; /*imaginary*/ for (int t = 0; t < n - 1; t++) { re = 0; im = 0; for (int f = 0; f < n - 1; f++) { re += A[f].getReal() * Math.Cos(2 * Math.PI * t * f / n); im -= A[f].getImaginary() * Math.Sin(2 * Math.PI * t * f / n); } s[t] = (re + im) / n; } return s; }
/* newDFTFunc Purpose: Forward DFT for a double array of samples of size n. This converts data in the time domain to the frequency domain. This will perform pythagorus to convert the complex array directly to usable data for the frequency domain chart. Parameters: s: Signal we are changing n: Size of the signal */ public double[] newDFTFunc(double[] s, int n) { double[] amplitude = new double[n]; double temp; newComplex cmplx; double re; /*real*/ double im; /*imaginary*/ for (int f = 0; f < n - 1; f++) { re = 0; im = 0; for (int t = 0; t < n - 1; t++) { re += s[t] * Math.Cos(2 * Math.PI * t * f / n); im -= s[t] * Math.Sin(2 * Math.PI * t * f / n); } cmplx = new newComplex(re, im); temp = (cmplx.getReal() * cmplx.getReal()) + (cmplx.getImaginary() * cmplx.getImaginary()); temp = Math.Sqrt(temp); amplitude[f] = temp; // These are the points we are going to plot. } return amplitude; }
/* runningDFT Purpose: This is the DFT function that will be used with threads. This will take in the number of threads specified by the user, and run DFT for that selection on the whole array. This will then be set to a speccific array for that thread number and used back in the threadDFT funciton to copy the array to the array that will be passed back to the windows form. Parameters: s: Wave data that will be processed n: Length of the wave to be processed threadNum: Current thread being run maxThreads: Number of threads specified by the user */ private void runningDFT(double[] s, int n, int threadNum, int maxThreads) { int thNum = threadNum; double temp; newComplex cmplx; double re; //real double im; //imaginary int startP = ((n / maxThreads) * (thNum - 1)), endP = ((n / maxThreads) * (thNum)); if(startP < 0) { startP = 0; } if (thNum == maxThreads - 1) { endP = n; } for (int f = startP; f < endP; f++) // run through first half { re = 0; im = 0; for (int t = 0; t < n - 1; t++) { re += s[t] * Math.Cos(2 * Math.PI * t * f / n); im -= s[t] * Math.Sin(2 * Math.PI * t * f / n); } cmplx = new newComplex(re, im); temp = (cmplx.getReal() * cmplx.getReal()) + (cmplx.getImaginary() * cmplx.getImaginary()); temp = Math.Sqrt(temp); threadAmplitude[f] = temp; // These are the points we are going to plot. } }