1

私は、いくつかの作り上げられた言語で書かれたスクリプトを解析し、そのスクリプトを使用していくつかの計算を行うプログラムを書いています。この言語には、タイプの外部OCaml関数を呼び出すために使用される特定の構造があり'a -> boolます。だから、言語の真ん中で私たちは持っているかもしれません

blah blah function (foo 45) blah blah

パーサーに次のようなコンストラクターを使用してもらいたい

OCamlFunction of ('a -> bool) * 'a

そのビットを値として解析します

OCamlFunction (foo,45)

ここで、「foo」は、ユーザーが別の.mlファイルで提供する必要があり、パーサーが事前に知らない関数です。「foo」が定義されているOCamlファイルの名前のみが実行時にパーサーに渡されます。したがって、string->型の関数を定義する必要があります('a->bool)。これは、ある関数の名前を取り、その関数を返します。

私の質問は次のとおりです。

(1)コードの動的ロードではDynLink.loadfileを使用する必要があると想定しています。これは行く方法ですか?

(2)識別子の知識から関数「foo」にアクセスするにはどうすればよいですか?(これは私をcamlp5に導きますか?)

4

2 に答える 2

2

loadfileOCamlにはそのようなサポートがなく、関数はコードを実行するだけなので、名前へのアクセスを提供しないため、名前で関数を直接ロードすることはできません。

ロードされたコードで使用されるメインプログラムで、ある種の関数登録APIをサポートする必要があります。したがって、ロードされたコードは次のようになります

ParserEngine.register_function "foo" foo_impl

Camlp {4,5}を使用してこの定型コードの生成を自動化することもregister_functions、関連付けリストを使用して最小化する呼び出しを行うこともできます。

register_functions次に、関数をハッシュテーブルや可変アソシエーションリストなどの内部構造に格納し、パーサーコードがアクセスできるようにします。

于 2011-03-11T01:03:52.407 に答える
2

別の解決策は、スクリプト全体を引用符で囲み、各ocaml値を引用符で囲むようにすることです。これは、たとえばCamlp4で実行できますが、構文上のコストがわずかにかかります(<< >>コード$ $周辺、OCaml値周辺)。スクリプトの解析はコンパイル時に実行されるため、OCamlタイパー自体が参照するOCaml値も明確に定義されていることを確認できます。さらに、より細かいタイプコントロールが得られます。

于 2011-03-11T06:02:45.233 に答える