Как выложить функцию w.r.t. его необязательные аргументы в OCaml - PullRequest
5 голосов
/ 10 марта 2012

Предположим, что функция bind имеет помеченный аргумент, необязательные аргументы и немаркированные аргументы, и вы хотите определить метод m, который применяет немаркированные аргументы bind и возвращает частично примененную функцию, так что пользователь m может применять помеченные или необязательные аргументы bind. Как ты это делаешь? Простая запись method m = bind a b [...] z заставляет компилятор думать, что необязательные аргументы опущены.

1 Ответ

11 голосов
/ 10 марта 2012

Важна позиция необязательных аргументов (в объявлении или типе функции): они применяются неявно только при применении следующего необязательного аргумента.

Если вы хотите частичное применение одного из нихпараметр p, чтобы не применять необязательный параметр ?o, поставить ?o после p в объявлении функции.

Контраст

# let f ?o p ~z = ();;
val f : ?o:'a -> 'b -> z:'c -> unit = <fun>
# f 1;;
- : z:'_a -> unit = <fun>  (* ?o applied *)

с:

# let f p ?o ~z = ();;
val f : 'a -> ?o:'b -> z:'c -> unit = <fun>
# f 1;;
- : ?o:'_a -> z:'_b -> unit = <fun> (* ?o not applied *)

Если вы не хотите изменять порядок определения или хотите частично применить все необязательные параметры, вам необходимо явно захватить необязательные параметры, которые будут неявно переданы:

# (fun ?o () -> f ?o 1 ~z:2);;
- : ?o:'a -> unit -> unit = <fun>

В случае, если вы не были знакомы с этим, синтаксис ?o на сайте вызова очень удобен для этого: он принимает 'a option и правильно делает прозрачную передачу необязательного аргумента, независимо от того, применен он или нет, к вызываемому объекту..

Я добавил последний параметр (), чтобы сохранить свойство, что после необязательных есть хотя бы один необязательный аргумент.Можно этого не делать, но это сложно и не рекомендуется.

...