FFTとか

- 2008-07-03-1

#この記事は4月頃書かれたものを再投稿したものです。 FFT出来無いとか馬鹿にされた(マジむかつく)のでFFTの事をちょっと。

スパコにもフーリエ変換、正変換FFT逆変換IFFTのクラスが用意されている。

FFT

FFTクラスはデカルト座標で配列をずらっと吐いてくるのでその配列を操作する事でスペクトル解析、フィルタリングなど各操作をする。 出てくる配列はこんな感じ。order: DC, nyquist, real 1f, imag 1f, real 2f, imag 2f, ... real (N-1)f, imag (N-1)f

また窓の種類が選べてrectangular、Welch、Hannの三つ。デフォルトではWelch。(レクトアングルとハニングはわかるけど、ウェルチとはどんな窓なんですか?) またIFFTに突っ込む前にデータ変換するためのPV UGensというクラス郡も用意されていて、各種比較、演算オンセット・ディテクトなどいろいろある。 詳しくは FFT Overview.html

では一つヘルプから例を、

周波数成分をプロットしてグラフを見る。スペクトルアナライズ。b = Buffer.alloc(s,1024);

a = { FFT(b, LFSaw.ar(400)); 0.0 }.play; ( b.getn(0, 1024, { arg buf; var z, x; z = buf.clump(2).flop; z = [Signal.newFrom(z[0]), Signal.newFrom(z[1])]; x = Complex(z[0], z[1]); {x.magnitude.plot}.defer }) ) a.free; b.free;

[説明]

b = Buffer.alloc(s,1024); //FFTデータを書き込むバッファが必要。

z = buf.clump(2).flop;

//clumpしてflopすると奇数、偶数つまり振幅成分と位相成分のデータ配列に分ける(clump(2)はサイズが2のセルを配列の先頭から順番に作っていく、結果2DArrayになる。flopは2DArrayの行と列をひっくり返す)

z = [Signal.newFrom(z[0]), Signal.newFrom(z[1])];

//newFromは別の配列から新たに配列を作る(でもこれzの要素をまたzの要素に入れ子にして意味あるんかなこれ)

x = Complex(z[0], z[1]);

//パワースペクトルを対数表示するのでComplexを使って

x.magnitude.plot

//実部と虚部から距離を取って最後にプロット

20080408-fft00.jpg

追記: ウェルチ窓についてSignal.htmlヘルプにグラフ見るコードが。

Signal.welchWindow(1024).plot;

20080408-hanni.jpg

20080408-welch.jpg 上がハニングで下がウェルチ。なるほどね。

追記2:

スパコのFFTでは窓かけやオーバーラップを自動でやってくれていて、 オーバーラップの深度はFFTの引数"hop"で0~ 1のunipolarでこれは0~100のパーセンテージ。 wintypeが窓の種類で -1 rectangular, 0 Welch, 1 Hannとなっている。

FFT.new(buffer, input, hop, wintype, active)

FFT