Скажем, я пишу этот код:OCaml: в качестве ключевого слова в сопоставлении с образцом ведет себя странно
# type t = A of int * int
let f = function A (i1, i2) -> print_int i1;;
type t = A of int * int
val f : t -> unit = <fun>
совершенна, она работает.
Теперь, скажем, у меня есть эта замечательная функция:
# let print_couple (i1, i2) = print_int i1; print_int i2;;
val print_couple : int * int -> unit = <fun>
Так что, как вы ожидаете, я хотел бы написать следующее
# let f = function A (_ as c) -> print_couple c;;
Ну, я не могу
Error: The constructor A expects 2 argument(s),
but is applied here to 1 argument(s)
Я задавался вопросом, это из-за _
или круглых скобок (я серьезно сомневался в этом, но я хотел быть исчерпывающим)?
# let f = function A _ -> failwith "Fight me"
let g = function A (_) -> failwith "1o1";;
val f : t -> 'a = <fun>
val g : t -> 'a = <fun>
Нет, это не ...
О, может быть, я должен показать компилятор, я знаю, у меня есть два аргумента:
# let f = function A ((_, _) as c) -> print_couple c;;
Error: The constructor A expects 2 argument(s),
but is applied here to 1 argument(s)
Но ... Если я пишу
# let f = function A (_, _) -> failwith "Puppey style";;
Это работает. Тогда почему, поскольку компилятор знает, что я ожидаю пару, и я даже пытаюсь дать его ему, он продолжает терпеть неудачу? Это то, что написав A (_ as c)
Я называю, независимо от того, первый аргумент? Странно, не так ли?
Я имею в виду, если я пишу
# let rec f = function
| [] ->()
| hd :: tl -> print_couple hd; f tl;;
val f : (int * int) list -> unit = <fun>
компилятор не будет беспокоить меня об этом списке, являющемся ассоциативном список или список целого? Тогда странно ли от меня ожидать такого же поведения от
# match a with
| A c | A (_ as c) | A ((_, _) as c) ->()
?
Благодаря Джоффри. Как всегда, ясный и лаконичный. :-) – Lhooq
О твоем редактировании, не правда ли, странно? Потому что, если я ожидаю два параметра, я ожидал бы (_, _). Я думаю, это просто синтаксический сахар, потому что вы часто хотите сопоставлять только конструктор, не принимая во внимание параметры, но вы не можете позволить что-то вроде (_ как c), потому что «c» не будет парой. – Lhooq