[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[dennou-ruby:000713] Re: FFTライブラリ



高橋@北大様:

ruby で FFT を使えるようにするための方針についてメモを作りました。
このメールの末尾につけます。基本的にこれに従って作って頂ければい
いのですが、舌足らずな点や間違い、認識不足もあるかもしれませんの
で、何かありましたらお知らせ下さい。

なお、もし C によるプログラミングの経験があまりなければ、C の勉
強をお願いします。とりあえずポインターの理解は必須です。前にも書
きましたが、入門書を読み、演習問題を実際にプログラミングして慣れ
て下さい。

さらに、ruby 用の C プログラミングのお作法を身につけて頂くことも
重要です。ruby本 (byまつもと・石塚) に乗ってる解説に加えて、ruby 
のソースに含まれている README.EX.jp というファイルを良く読んでく
ださい。こちらのほうが ruby 本より詳しいそうです。お作法の例です
が、作業のために一時的に記憶領域を確保する場合、alloca または 
ALLOCA_N を使います。auto 変数では対応できない場合のみ、xmalloc
を使ってください。xmalloc は malloc の変りに使うruby 用の関数で
す。malloc は使わないで下さい。他にも、例外の扱いも理解するなど
必要ですし、extconf.rb によるインストールの自動化も行う必要があ
ります。ruby のソースは C で書かれてますので、困ったら(困らなく
ても) ruby のソースを読んで、出来るだけまねをしてください。プロ
グラミングについては模倣は本当に発明の母です。模倣を経ずして創造
はないと思って、どんどん模倣してください。

プログラム作成時には、ステップバイステップでやって下さい。何か関
数を書いたら、その度にテストして動作を確認してください。面倒に思
うかもしれませんが、沢山書いてから初めてテストすると、動かなかっ
た場合は直すのが大変です。一つ一つ品質保証していくほうが、結局は
速いです。要求仕様を満たすためにはどうすればいいかを考えることは
最初から必要ですが、製品を作る際は、まず機能が限られた簡単なもの
を作り、動作をちゃんと確認して、少しづつ太らせていくといいでしょう。

製品は夏休み明けぐらいに出来るようなペースでお願いします。そのた
めにはそれよかなり早い段階で、簡易バージョンがリリース出来る必要
があるでしょう。簡易版でもこまめにリリースして、この場にアナウン
スしてください。

それでは、大変だとは思いますが、頑張ってください。

--
堀之内 武                    horinout@xxxxxx
京都大学宙空電波科学研究センター     611-0011 宇治市五ヶ庄
===================================================================

       FFT を ruby で使えるようにするための要求仕様(覚え書き)

			2001/06/07   堀之内 武

● 必要な機能

1 複素フーリエ変換 (順・逆)

2 実フーリエ変換 (順・逆)

3 sine 変換 (順・逆)

4 cosine 変換 (順・逆)

● 演算対象

多次元数値型配列 NumArray
(http://www.kurasc.kyoto-u.ac.jp/radar-group/members/kawanabe/numarray.html)
を用いる(入出力とも)。

NumArray は double 型の実数と double 型の実・虚部をもつ複素数をサポー
トしているので、FFT は double 型の変数に対応出来れば良い。ただし、将来
float が加わる可能性はある。整数については直接はサポートせず、実数に 
変換することで対応できればよい。

● 多次元配列の扱い

Fourier 変換はある次元にそって1次元的に行うものである。
多次元配列に適用する場合は、以下のようにする。

  1. 何次元めに対して FFT を適用するかを指定し、その次元に関する変換を
     行う。次元は 1,2,3..でなく、0,1,2,.. で数える。(つまり1次元目は
     ゼロ)

  2. 何次元目についてかが指定されなかった場合、すべての次元に関し
     それぞれに FFT を行う。従って例えば3次元配列なら3回FFTが行われる。

● FFT ライブラリーの名前

FFT ライブラリーは NumArray 同様 num というディレクトリーに入れること
にし、fft.so という名前になるようにする。すると、ruby プログラム内で

require "num/fft"

と呼べば使えるようになる(但し、numディレクトリーは ruby のライブラリー
サーチパスにインストールしておくか、num の直上のディレクトリーでプログ
ラムを実行すれば)。

● 機能追加型に

FFT 機能は NumArray のインスタンスメソッドとする。ただし、numarray.c 
を直接編集してはいけない。独立したファイルにして require すれば 
NumArray に FFT を行うメソッドを追加するようにする。FFT の結果も 
NumArray が返るようにする。これは、require "num/fft" をしたときに、メ
ソッドを追加する呼出しが行われるようにすることで対応する。

● メソッドの引用仕様

FFTの各メソッドを、ruby で使う際の仕様は以下のようにする。

NumArrayのインスタンスメソッド

  *  fft(dim)	複素FFT(順)。dimはFFTを行う次元(整数)。dimを省略するか、
		負の値を与えれば、すべての次元それぞれについて FFT を
		を行うものとする。

		使用例: ary を NumArray のオブジェクトとすると、

			ary.fft(0)  1次元目に関するFFT
			ary.fft(2)  3次元目に関するFFT (もしも ary が2
				    次元以下の配列なら例外を発生する)

  *  ffti(dim)  複素FFT(逆)。引数 dim の仕様は fft と同様。

  *  rfft(dim)  実FFT(順)。引数 dim の仕様は fft と同様。

  *  rffti(dim)  実FFT(逆)。引数 dim の仕様は fft と同様。

  *  sinfft(dim)  sine FFT(順)。引数 dim の仕様は fft と同様。

  *  sinffti(dim)  sine FFT(逆)。引数 dim の仕様は fft と同様。

  *  cosfft(dim)  cosine FFT(順)。引数 dim の仕様は fft と同様。

  *  cosffti(dim)  cosine FFT(逆)。引数 dim の仕様は fft と同様。

● Fourier 変換する次元の長さについて。

長さが 2,3,5 の倍数である場合は FFTを行う。そうでない場合は、
Fast でない Fourier 変換を行う(下記の「利用ライブラリー」を
参照のこと)。

● エラー処理

エラーは「例外」を発生することで対処する。C では rb_raise という、ruby 
組み込みの raise に対応する関数を用いる。エラークラスとしては、
RuntimeError を用いてよいが、StandardError を継承して専用エラークラ
スを作ってもよい。エラーメッセージは内容を的確に表す英語にする必要があ
る。

● ドキュメンテーション

全メソッドに関する、使用のためのマニュアルを作る。フォーマットは RD に
する。NumArray のドキュメントがRD で書かれてますので、それをまねれば良
い。

● 利用ライブラリー

FFTのライブラリーは既存のものを利用する。

まずは、Netlib (http://netlib2.cs.utk.edu/) 収録の fftpack を使うと良
いだろう(http://netlib2.cs.utk.edu/fftpack/index.html)。fftpack は、
もともと Fortran で書かれているが、C で書き直したものがあるのでそれを
使えば良い(http://netlib2.cs.utk.edu/fftpack/fft.c)。ソースは単精度
(float)であるが、定数表現は倍精度(double)にもそのまま使えるようになっ
ているので、ソース中の "float" を "double" に置き換えるだけで、double 
に対応出来ると思われる。但し動作確認は必要。

FFTPACK は任意の長さの次元の Fourier 変換が出来るようである。ソースを
少し見たところ、少なくとも 2,3,5 の倍数では FFT になるように見える。そ
うでなくても (効率はともかく) 基本的に FFT するように見えるが、嘘かも
知れない。でもとにかく Fourier 変換は出来る。FFTPACKのライセンス形態は
不明であるが、Netlib に置いてあるソースにはコピーライトに関する記述が
全くないことから、恐らく全く主張してないものと想像される。

FFTPACK の計算がどれくらい速いかは知らないが、恐らくベストではない。
よって、発展として、余力があれば、他の FFT も使えるようにすると良い:

   1. 非ベクトルマシーンで fftw がインストールされていれば、fftw を使
      うようにする ( http://www.fftw.org/ または 
      http://netlib2.cs.utk.edu/transform/index.html)。インストールさ
      れているかどうかはコンパイル時にチェックするするようにする。
      どうやってチェックするかは ruby 本 (まつもと・石塚) の、mkmf の
      項を参照のこと。

   2. ベクトルマシンでは、石岡@東大さんの ISPACK 中の FTPACK を使うと
      良い。

上記2つのソフトのライセンスは、GPL(fftw), LGPL (ISPACK) である。

---
堀之内 武 (horinout@xxxxxx)