写一个析取模式的函数绑定相同的变量

时间:2013-06-13 06:28:30

标签: ocaml coq

我有这种类型

Inductive coef :=
| Mycoef_ex2 : matrix -> coef
with matrix :=
| My_matrix : list (list coef) -> matrix.

Inductive my_type :=
| Mytype_ex1 : list my_type  -> my_type
| Mytype_int : Z -> my_type
| Mytype_coef : coef -> my_type.

Ocaml我可以写:

let test_mytype := function
| Mytype_ex1 [Mytype_coef (Mycoef_ex2 (My_matrix m)); Mytype_int i] :: ps -> ...

我想在我的函数需要两个参数的同一函数中使用参数mi。但是在Coq我不能这样做,例如,如果我写入{{ 1}}

Coq

我收到了一个错误:

Definition test_mytype (m: my_type) :=
 match m with
  | Mytype_ex1 (Mytype_coef (Mycoef_ex2 (My_matrix m)))
  | Mytype_int i :: ps => my_function m i
   ...
 end.

如果我写下这个功能,Toplevel input, characters 82-215: Error: The components of this disjunctive pattern must bind the same variables. 会被接受,但我不能同时使用Coqm

i

我也尝试使用匹配例如:

Definition test_mytype (m: my_type) :=
 match m with
  | Mytype_ex1 (Mytype_coef (Mycoef_ex2 (My_matrix m))) :: ps => ...
  | Mytype_ex1 (Mytype_int i) :: ps => ...
    ...
 end.

但我的问题是Definition test_mytype (m1, m2: my_type) := match m1, m2 with | Mytype_ex1 (Mytype_coef (Mycoef_ex2 (My_matrix m))) :: ps, | Mytype_ex1 (Mytype_int i) :: ps => ... ... end. m应该属于同一个i

您知道如何在m: my_type中同时编写可同时使用test_mytypem的函数i吗?

2 个答案:

答案 0 :(得分:6)

您似乎没有很好地掌握析取模式的内容。

在OCaml

我们假设,例如,我在OCaml中定义了一个类型either

type either = Left of int | Right of int

因此,either类型的值只是标有LeftRight的整数。

我现在可以编写的一个明显的函数是int_of_either,它将either类型的值作为其参数,并生成一个整数作为结果:

let int_of_either = function
  | Left x -> x
  | Right x -> x

现在,请注意LeftRight的案例具有相同的右侧。在这种情况下,析取模式允许我通过使模式匹配的两个臂共享一个右侧来使我的函数更简洁:

let int_of_either = function
  | Left x
  | Right x -> x

当然,只有在两种模式中绑定变量x时才能解决这个问题。 (此外,绑定应该是一致的,因为它们应该就x的类型达成一致。这里,它们都会将x绑定到类型int的值。)

也就是说,如果我写,例如

let int_of_either = function
  | Left x
  | Right y -> y

编译器将拒绝我的程序并抱怨y Left没有发生either

  

错误:变量y必须出现在此|的两侧图案

在Coq中

以类似的方式,如果在Coq中我定义了类型Inductive either := | Left : Z -> either | Right : Z -> either.

int_of_either

和一个函数Definition int_of_either (e : either) : Z := match e with | Left x => x | Right x => x end.

int_of_either

然后我可以使用析取模式将Definition int_of_either (e : either) : Z := match e with | Left x | Right x => x end. 重写为

Definition int_of_either (e : either) : Z :=
  match e with
  | Left x
  | Right y => y
  end.

但是,如果我写

{{1}}

编译器抱怨

  

错误:此析取模式的组件必须绑定相同的变量。

这正是你得到的错误。


总之,我建议暂时忘记析取模式,并首先尝试使用专用右侧为模式匹配的每个臂定义函数,然后再考虑是否可以稍微编写函数紧凑的形式。

答案 1 :(得分:2)

 match m with
  | Mytype_ex1 (Mytype_coef (Mycoef_ex2 (My_matrix m)))
  | Mytype_int i :: ps
     => my_function m i

错了,不能工作。不仅第一个匹配my_type和。{ 第二个my_type list,但是以析取模式(或模式) 双方必须捕获相同的变量:它没有意义 在案例中定义m,在另一个案例中定义i,并期望两者都成立 在分支中定义。

所以我不知道你要做什么,但Coq和OCaml有 这里的限制相同,并且应该没有区别。