本実験で作成するインタプリタプログラムは,以下の 7 つのファイルから構成される.
-
syntax.ml
- このファイルでは,抽象構文木のデータ構造を定義して
いる.抽象構文木は構文解析の出力であり,解釈部の入力なので,インタプ
リタの全ての部分が,この定義に(直接/間接的に)依存する.
- parser.mly
- C 言語に yacc や bison といった構文解析プログラム
生成ツールがあるように,Objective Caml にも ocamlyacc というツールがあり,
.mly という拡張子のファイルに記述された文法定義から,構文解析プロ
グラムを生成する.文法定義の仕方は yacc と似ている.
- lexer.mll
- C 言語に lex, flex といった字句解析プログラム生成ツー
ルがあるように,Objective Caml にも ocamllex というツールがあり,.mll と
いう拡張子のファイルに定義されたトークンとなる文字列のパターン定義か
ら,字句解析プログラムを生成する.パターンの定義の仕方は lex と似て
いる.
- environment.mli, environment.ml
- インタプリタ・型推論で用いる,環境と呼ばれる
データ構造を定義する.
- eval.ml
- 解釈部プログラムである.構文解析部が生成した構文木から
計算を行なう.
- main.ml
- 字句解析・構文解析・解釈部を組み合わせて,インタプリ
タ全体を機能させる.プログラム全体の開始部分でもある.
最初に扱う ML1 インタプリタのための7つのファイルに加え,インタプ
リタをコンパイルするための Makefile を http://www.sato.kuis.kyoto-u.ac.jp/~igarashi/class/isle4/src/に置い
てある.これら 7 つのファイルを同じディレクトリに保存し,どれかひとつ
の .ml ファイルを Emacs に読み込む. そのバッファでC-c C-c とす
ると,コンパイルのコマンドを聞かれるので, make depend とする.この
作業は初回のみ(正確にはファイルが増えた時もしくはmake cleanを行なっ
た後)行えばよい. 次に,C-c C-c make -k とする. すると,ソース
ファイルのあるディレクトリに miniml という実行形式ファイルが生成される.
(M-x shellでシェルモードに 入って) miniml を起動すると #というプロ
ンプトが現れるので, MLプログラムを打つと結果が表示される.
> miniml
# x;;
val - = 10
# x + 3;;
val - = 13
(起動時に大域変数 x の値は 10 になっている.)
ソースを変更したあとは,C-c C-c make -k でコンパイルすることにな
る.コンパイル時にエラーが発生した場合は M-x next-error とすることで,
エラーの発生した場所にカーソルが移動する.
実行可能ファイルとなった Objective Caml プログラムをデバッグするには
ocamldebug を使用する方法(Objective Camlマニュアル16章参照)と,インタラクティ
ブコンパイラ ocaml にプログラムを構成する各モジュールをロードして,
テストする方法がある.ocaml を起動する際に
ocaml -I<モジュールのあるディレクトリのパス> foo.cmo bar.cmo ...
のようにオブジェクトファイルを指定すると,Foo, Bar という
モジュールが利用できるようになるので,トップレベルでテストする
ことが可能になる.