4 オブジェクト指向スクリプト言語Ruby

4.1 特徴

 オブジェクト指向スクリプト言語「Ruby」は,1993年,まつもとゆきひろ氏を中心とする,有志数名によって作られた.Rubyには,以下のような特徴がある.Perlに匹敵する文字列処理能力などの一般的な特徴はここでは省き,計算惑星科学にとって重要であるものをここに挙げる.

 オブジェクト指向言語であること,シンプルな文法,ガベッジコレクタ,ループを抽象化する「イテレータ」の存在,対話インタフェースの存在などの特徴は,すべてプログラミングを容易にするものである.これは,プログラミング作業そのものに煩わされること無く研究本体に専念する事を可能にし,開発効率を向上させることを意味している.また,RubyはもともとUNIX環境で製作されたプログラミング言語であるが,設計段階でプラットフォームに依存しない実行環境を目指して製作されている.ひとつのスクリプトを数多くのUNIX系OSはもちろんWindowsやMacintoshなどのOS上でも同様に実行する事ができる.この様なプログラミング言語がGPLに従って無償で配布されていることも,導入を容易にするという点においてRubyの可搬性を優れたものとしている.

 つぎに,他のプログラミング言語と比較した際のRubyの利点について述べる.科学計算においては,数値計算やグラフィックの為のライブラリが豊富な C, FORTRAN77, FORTRAN90などがよく用いられるが,いずれもコンパイラ言語であり,試行錯誤の段階でのコンパイル作業は時間のロスが大きい.コンパイラ言語はアプリケーション開発者の為のもので,エンドユーザが用いるには手間が多すぎるといえる.

 また,大気科学,及び海洋学などの分野においてよく用いられるアプリケーションとして,GrADSが挙げられる.GrADSでは,データを単なる多次元の配列としてではなく,単位と座標を持った自己記述的な物理量として扱うことよって,データ解析を迅速かつ容易に行うことを可能にしている.しかしGrADSでは扱うことのできるデータフォーマットが限られており,ユーザの欲求を必ずしも満たすものではない.また,GrADSはプログラミング言語として完全ではないので,カスタマイズ性と自動化の面に難がある.

 さらには,対話的に使用する事のできるプログラミング言語として, IDL, Matlab (そのクローンとしてOctave), yorick などがある. IDL, Matlab は商用プログラミング言語であり,広範囲なグラフィック機能と数学ライブラリを備えている.これらは,今までの中では最良の選択であったかもしれないが,それでもいくつかの欠点が存在する.一つ目は,これらの言語はオブジェクト指向言語ではない事である.すなわち,これらの言語は柔軟性に欠け,汎用アプリケーションを開発する目的には向かない事を意味している.例えば,ファイルフォーマットによらないようにデータの扱いを統一する事は困難な作業となるであろう.IDLの最近のバージョンではオブジェクト指向の特徴が組みこまれてはいるものの,実用的ではない.二つ目の欠点として挙げられるのは,何より IDL や Matlab は有償の商用ソフトウェアであり,ソースが公開されていないと言う事である. Octaveやyorickはオープンソースであるものの,機能的には十分ではない.また,使用する事のできるプラットフォームが制限される.これらの言語はスーパーコンピュータにおいてはメーカー側が対応しない限り使用する事ができない.三つ目は,Cなどの他の言語によって言語を拡張する事が難しいと言う事である.商用ソフトウェアであり,ソースコードが公開されていない点もユーザによる拡張を妨げる要因となっている.この点に関しては,Rubyは奇跡的とも言えるほどにC言語による拡張性が高い.本論文で紹介している NumRu/fft ライブラリも,この特徴の賜物といえる.

4.2 オブジェクト指向

 この節では,オブジェクト指向という方法論について簡単に説明する.オブジェクト指向とは,最も簡単に要約するなら,その名の示す通り「オブジェクトを中心にした考え方」である.より詳しく表現するなら,次の三つの概念に象徴されている.

 カプセル化とは,あるデータと,それに対する手続きを一体化し,あるデータへのアクセスを決められた手続きだけに限定して行うようにする事である.これにより,ある関数について入力と出力さえ把握していれば,関数の中で何が行われているかを気にする必要がなくなる.それを実現するのが,クラスという考えかたである.クラスとは,あるオブジェクトについて特徴を抽象化し,一つのグループとしてまとめたものである.つまり,オブジェクトをクラスにまとめる事がカプセル化と同義とも言える.Rubyでは,すべてのデータがオブジェクトとして扱われていて,オブジェクトの内部の状態がメソッドを経由する以外の方法では外部からアクセスする事ができないことにより,カプセル化を実現している.

 ポリモーフィズムとは,多態性とも言い,「オブジェクトは,己がどう振る舞うべきかを知っている」という言葉に象徴されている.例えばRubyには,文字列 str = "abcdef" があったときにその文字列の長さを知りたい時は「length」というメソッドが存在していて,つぎのように実行する.

ruby> str = "abcdef"
ruby> print str.length
6

また,配列 ary = [1,2,3,4,5,6] があったときに配列の長さを知りたい時にも,「length」メソッドが用いられる.

ruby> ary = [1,2,3,4,5,6]
ruby> print ary.length
6

内部的には文字列の長さを調べる行為と配列の長さを調べる行為は異なっている.しかしそれぞれのオブジェクトに対して「length」(長さを知りたい)というメッセージを送った時に,それぞれのクラス内で定義されている適切なメソッドを選んで実行している.実際に作業を始める段階になってから,対象となるオブジェクトに応じてどの具体的な手続きを適用するか決定されるので,動的結合と呼ばれる事もある.ポリモーフィズムによって,例えば,この「length」と言うメッセージが新しいクラスに対応しなければならないとき,新しいクラスの側を正しく定義すれば,メッセージを送る側のルーチンを一切書きかえることなしに,「length」ルーチンを拡張する事ができる.

 最後に継承について述べる.これは,ある雛型となるクラス(スーパークラスと言う)から,少しだけ特徴の異なる新しいクラス(サブクラスと言う)を定義することを指す.クラスがデータと手続きの集合体であることを思い出せば,クラスを継承することによって資源を節約しつつ,効率と見通しの良いプログラミングが可能となると言える.例を用いて説明すると,「柴犬」というクラスがあったとき,この柴犬クラスは「犬」というスーパークラスを継承している、と言う事ができる.同様に,「チワワ」クラスも,「犬」スーパークラスのサブクラスと言える.「柴犬」クラスと「チワワ」クラスは共通した性質を持つ部分もあるが,それぞれ異なる性質を持つ部分も存在する.このように,共通した部分を共有しながら,違っているところだけを定義しなおすことで,新しいクラスを定義するのが,継承という方法である.継承を用いたプログラミング方法を,差分プログラミングと呼ぶ.

 以上に挙げたような特徴を有効に活用することで,より効率的でミスの少ない,理解しやすいプログラミングが可能となる.Rubyは,このオブジェクト指向という考えかたを徹底して導入したプログラミング言語である.

4.3 拡張ライブラリ

 Rubyは,処理の細部は言語に任せて人間は問題の本質に集中できるよう,開発効率を向上させるように設計されている.その一方で,プログラムを実行する際の実行速度は,インタプリタであるという要因もあり,Ruby単体で数値計算を行うには非常に遅い.そこで,C言語,もしくはC++によって拡張ライブラリをプログラミングし,Rubyに対して静的,ないし動的に組み込むことで,Rubyの最大の欠点ともいえる実行速度の遅さを克服することが可能となる.拡張ライブラリを作成するに当たって,RubyにはC言語用のAPI(Application Programming Interface)が用意されており,C言語で記述された関数を呼び出したり,CからRubyの機能を呼び出したりする事を容易にしている.Rubyインタプリタ自体もコアとなる部分以外はこのC言語APIを用いて記述されている.この拡張機能を使うことで,Cから使える,すなわちCやC++,FORTRANで記述された既存のライブラリをRubyからアクセスできる様にして,柔軟かつ高速なアプリケーションを作成することが可能となる.

 拙作「NumRu/fft」ライブラリも,C言語で記述し,高速フーリエ変換のルーチン自体は既存のライブラリである,FFTWおよびISPACK(予定)を利用している.