Coq 从其他文件引用类型变量时出错

Coq 从其他文件引用类型变量时出错,coq,Coq,我正在coq中研究群体理论的形式化。我有两个文件: v-包含群的定义和定理 群_Z.v-包含Z群的定理和定义 第五组: Require Import Coq.Setoids.Setoid. Require Import Coq.Lists.List. Require Import PeanoNat. Class Semigroup G : Type := { mult : G -> G -> G; assoc : forall x y z:G,

我正在coq中研究群体理论的形式化。我有两个文件:

  • v-包含群的定义和定理
  • 群_Z.v-包含Z群的定理和定义
第五组:

Require Import Coq.Setoids.Setoid.
Require Import Coq.Lists.List.
Require Import PeanoNat.

Class Semigroup G : Type :=
{
    mult : G -> G -> G;
    assoc : forall x y z:G,
        mult x (mult y z) = mult (mult x y) z
}.

Class Monoid G `{Hsemi: Semigroup G} : Type :=
{
  e : G;
  left_id : forall x:G, mult e x = x;
}.

Class Group G `{Hmono: Monoid G} : Type :=
{
    inv : G -> G;
    left_inv : forall x:G, mult (inv x) x = e;
}.

Declare Scope group_scope.
Infix "*" := mult (at level 40, left associativity) : group_scope.
Open Scope group_scope.

Section Group_theorems.

  Parameter G: Type.
  Context `{Hgr: Group G}.
  (* More theorems follow *)
  Fixpoint pow (a: G) (n: nat) {struct n} : G :=
    match n with
    | 0 => e
    | S n' => a * (pow a n')
    end.

  Notation "a ** b" := (pow a b) (at level 35, right associativity).

End Group_theorems.
Close Scope group_scope.
第五组:

Add LoadPath ".".
Require Import groups.
Require Import ZArith.

Open Scope group_scope.
Section Z_Groups.
  Parameter G: Type.
  Context `{Hgr: Group G}.

  Definition pow_z (a: groups.G) (z: Z) : G :=
    match z with
    | Z0 => e
    | Zpos x => pow a (Pos.to_nat x)
    | Zneg x => inv (pow a (Pos.to_nat x))
    end.

  Notation "a ** b" := (pow_z a b) (at level 35, right associativity).
End Z_groups.
Close Scope group_scope.
尝试定义
pow_z
失败,并显示以下消息:

术语“pow a(Pos.to_nat x)”的类型为“groups.G” 预期为“G”型

如果我们使用不同的签名:
定义pow_z(a:G)(z:z):G

而不是
定义pow_z(a:groups.G)(z:z):G

然后它给出了另一个错误:

术语“a”的类型为“G”,而预期的类型为 “G组”


如何解决这个问题?

在Coq中,命令
参数G:Type
声明了一个全局常量,这类似于将抽象类型的存在公理化
G:Type
。从理论的角度来看,这应该是可以的,因为这个公理是可以实现的,但是我认为您的意思是
变量G:Type
表示局部变量

Coq的错误消息随后出现,因为您声明了两个名为
G
的全局常量,每个模块中一个。一旦声明了第二个常量,第一个常量就由Coq指定为
groups.G
(这是最短的名称,可以消除此常量与其他常量之间的歧义)。现在
pow
操作并返回一个
groups.G
,而您需要
pow\u z
返回一个
G
(该位置的文件
groups\u z.v
中表示
groups\u z.G
,与
groups.G
不同)


NB:群论在Coq中已经发展了好几次,如果你想做任何事情而不是尝试这个系统,我建议你在现有库的基础上工作。例如,数学组件库在两个文件中都有一个。

我将
参数G:Type.
更改为
变量G:Type
,并将
pow_z
定义更改为:

Definition pow_z (a: G) (z: Z) : G :=
    match z with
    | Z0 => e
    | Zpos x => pow G a (Pos.to_nat x)
    | Zneg x => inv (pow G a (Pos.to_nat x))
    end.