4

私は非常に初心者の OCaml プログラマーなので、これがばかげた/明白な質問である場合はご容赦ください。吸収すべきことがたくさんあり、ドキュメントでこれを見逃している可能性があります。

次のようになり始めているコードのベースがあります。

let update_x p x =
  add_delta p;
  p.x <- x;
  refresh p

let update_y p y =
  add_delta p;
  p.y <- y;
  refresh p

let update_z p z =
  add_delta p;
  p.z <- z;
  refresh p 

次のようなものを書きたいので、重複が私を悩ませ始めています:

let update_scalar p scalar value =
    add_delta p;
    magic_reflection (p, scalar) <- value;
    refresh p

この方法で x を更新すると、次のように簡単に呼び出すことができます。

update_scalar p 'x' value

これは「マクロ!」と呼びます。しかし、OCaml にマクロ システムがあるとは思えません。他に何ができますか?

4

3 に答える 3

5

やりたいことを完全に行うことはできませんが、高次関数を使用してボイラープレートを大幅に削減できます。

let update_gen set p x =
  add_delta p;
  set p x;
  refresh p

let update_x = update_gen (fun p v -> p.x <- v)
let update_y = update_gen (fun p v -> p.y <- v)
let update_z = update_gen (fun p v -> p.z <- v)

OCaml にはマクロ システム (camlp4) があり、多少の作業を行うことで、この種のものを実装できます。

于 2008-11-05T05:14:44.190 に答える
1

いいえ、プレーンなOCamlではやりたいことができません。camlp4(マクロシステムの一種ですが、おそらく慣れているものとは異なります)を使用して構文拡張を記述し、変換することができます。

UPDATE_FIELD x f y

の中へ

x.f <- y

または、ハッシュテーブルにデータを詰め込んで、型の安全性を放棄することもできます。

注:OCamlバージョン3.10以降に含まれているcamlp4のバージョンは、以前のバージョンとは異なり、互換性がありません。最新バージョンについては、OCamlチュートリアルサイトを参照してください。

于 2008-10-19T02:06:01.763 に答える
0

上記のように、ocaml にはマクロ システムがあります。そして、このタスクには、ほんの一部しか必要ありません:

open Printf

type t = { mutable x : float; mutable y : float; mutable z : float; mutable t : int; }

let add_delta p = p.t <- p.t + 1
let refresh p = printf "%d) %.2f %.2f %.2f\n" p.t p.x p.y p.z

DEFINE UPD(x) = fun p v ->
  add_delta p;
  p.x <- v;
  refresh p

let update_x = UPD(x)
let update_y = UPD(y)
let update_z = UPD(z)

let () =
  let p = { x = 0.; y = 0.; z = 0.; t = 0; } in
  update_x p 0.1;
  update_y p 0.3;
  update_z p 2.0

コンパイル:

ocamlfind ocamlc -package camlp4.macro -syntax camlp4o q.ml -o q

生成されたコードを次のように表示します。

camlp4o Camlp4MacroParser.cmo q.ml
于 2011-01-24T13:16:43.427 に答える