FFTW3.x

ライセンスGPL
URLhttp://www.fftw.org/

フーリエ変換を行うライブラリです。
フーリエ変換の性質上複素数がでてくるので、そのあたりが少しややこしい、、、。

コンパイル

ver. 3.0.1

./configure --prefix=/c/mingwmakeで問題ないはずです。
ですが、DLLは作られません。

インクルード、リンク

インクルードは”fftw3.h”だけでOK。リンクオブジェクトはlibfftw3.aをリンクします。

基本的使用方法

2次元ならば大体以下のようなコードで事足ります。

#include <fftw3.h>

int main( int argc, char *argv[] )
{
	fftw_complex *in, *out;
	fftw_plan p;
	int i;
	unsigned int uiImageLength, uiImageWidth;

	/* 領域の確保 */
	in = fftw_malloc( uiImageLength * uiImageWidth * sizeof(fftw_complex) );
	out = fftw_malloc( uiImageLength * uiImageWidth * sizeof(fftw_complex) );
	
	/* inの実部に画像を詰め込む*/
	
	/* プランの作成 */
	p = fftw_plan_dft_2d( uiImageLength, uiImageWidth, in, out,
					 FFTW_FORWARD, FFTW_ESTIMATE );
	
	/* フーリエ変換の実行 */
	fftw_execute( p );
	
	/* プランの消去 */
	fftw_destroy_plan( p );
	
	/* FFT係数の正規化 */
	for ( i = 0; i < uiImageLength * uiImageWidth; i++ )
	{
		out[i][0] /= uiImageLength*uiImageWidth;
		out[i][1] /= uiImageLength*uiImageWidth;
	}
	
	/* 逆変換 */
	p = fftw_plan_dft_2d( uiImageLength, uiImageWidth, out, in,
					 FFTW_BACKWARD, FFTW_ESTIMATE );
	
	/* 領域の開放 */
	fftw_free( in );
	fftw_free( out );

	return 0;
}

データ型

fftw_complex型は、double[2]で、[0]は実部、[1]は虚部になっています。変換前に実数データをコピーするのは、[0]のほうで、[1]は0.0を入れておきます。

FFT変換の出力

FFTWで変換した結果は、複素数として出力されるのですが、「正規化はされていない」だそうで、
データを正規化するには、各データをデータ個数で割ればいいらしいです。
これをしないと、変換→逆変換でもとの画像を再構成できません。

そのほか

fftw_plan_dft_*()の最後の引数は、通常FFTW_ESTIMATEで問題ないらしいですが、
よくわかりませんがそのほかのモードもあります。

2次元配列を指定することもできますが、この場合配列順は添え字の後ろが先になります。
これはおそらく処理を高速にするためです。

実行結果

入力画像

入力画像

出力画像

出力画像

アーカイブ