2011-04-28 50 views
4

大家好 我正在使用fftw C庫來計算嵌入式系統上某些信號處理應用程序的頻譜。但是,在我的項目中,我遇到了輕微的尷尬。在C中使用fftw.h計算fft和ifft0

下面是我寫的一個簡單程序,用於確保我正確實施fftw功能。基本上我想計算12個數字序列的fft,然後做ifft並再次獲得相同的數字序列。如果你有fftw3和gcc安裝,如果你編譯這個程序應該工作:

gcc -g -lfftw3 -lm fftw_test.c -o fftw_test 

目前我FFT長度尺寸與輸入數組相同。

#include <stdio.h> 
#include <stdlib.h> 
#include <sndfile.h> 
#include <stdint.h> 
#include <math.h> 
#include <fftw3.h> 

int main(void) 
{ 
double array[] = {0.1, 0.6, 0.1, 0.4, 0.5, 0, 0.8, 0.7, 0.8, 0.6, 0.1,0}; 
//double array2[] = {1, 6, 1, 4, 5, 0, 8, 7, 8, 6, 1,0}; 
double *out; 
double *err; 
int i,size = 12; 

fftw_complex *out_cpx; 

fftw_plan fft; 
fftw_plan ifft; 
out_cpx = (fftw_complex*) fftw_malloc(sizeof(fftw_complex)*size); 
out = (double *) malloc(size*sizeof(double)); 
err = (double *) malloc(size*sizeof(double)); 

fft = fftw_plan_dft_r2c_1d(size, array, out_cpx, FFTW_ESTIMATE); //Setup fftw plan for fft 
ifft = fftw_plan_dft_c2r_1d(size, out_cpx, out, FFTW_ESTIMATE); //Setup fftw plan for ifft 

fftw_execute(fft); 
fftw_execute(ifft); 

//printf("Input: \tOutput: \tError:\n"); 
printf("Input: \tOutput:\n"); 
for(i=0;i<size;i++) 
{ 
err[i] = abs(array[i] - out[i]);  
printf("%f\t%f\n",(array[i]),out[i]); 
//printf("%f\t%f\t%f\n",(array[i]),out[i],err[i]); 
} 

fftw_destroy_plan(fft); 
fftw_destroy_plan(ifft); 
fftw_free(out_cpx); 
free(err); 
free(out); 
return 0; 
} 

產生以下的輸出:所以,很顯然

Input:  Output: 
0.100000 1.200000 
0.600000 7.200000 
0.100000 1.200000 
0.400000 4.800000 
0.500000 6.000000 
0.000000 0.000000 
0.800000 9.600000 
0.700000 8.400000 
0.800000 9.600000 
0.600000 7.200000 
0.100000 1.200000 
0.000000 0.000000 

的IFFT是生產一些放大的結果。在這裏找到的fftw文檔: fftw docs about scaling。 它提到了一些縮放,但我使用「r2c」和「c2r」轉換而不是FFT_FORWARD和FFT_BACKWARD。任何洞察力將不勝感激。

回答

4

看着the great documentation for the functions you use,你會看到你使用FFT_FORWARD和FFT_BACKWARD,以及它確切的位置。因此,先前找到的縮放信息也適用於此處。

+1

好的,謝謝,是的,我確實在某些時候讀過。它是一個漫長的一天......是解決與: 出[我] =出[我] /大小; – digiphd 2011-04-28 12:50:52

2

對不起,這是迂腐,但你的尺寸out_cpx是不正確的。而不是長尺寸,它應該是size/2 + 1。這是因爲真實信號的FFT是Hermitian。通過將out_cpx初始化爲某個隨機數(全部爲3.14159),可以驗證我說的是什麼。運行向前和向後,然後從size/2 + 1打印出out_cpx大小。它不會改變。

http://www.fftw.org/fftw3_doc/Real_002ddata-DFT-Array-Format.html#Real_002ddata-DFT-Array-Format

+0

非常感謝你我感謝你的意見:)現在閱讀文檔。 – digiphd 2011-05-06 04:15:18

1

R2C和C2R做基本上與常規傅立葉變換一樣。唯一的區別是輸入和輸出數組都需要保存一半的數字。請查看FFTW r2c and c2r手冊的最後一段。所以歸一化因子正好是實數的元素數,或者變量size(== 12)。