Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
617 views
in Technique[技术] by (71.8m points)

coq - Error when referencing type variable from another file

I am working upon formalization of groups theory in coq. I have 2 files:

  • groups.v - contains definitions and theorems for groups
  • groups_Z.v - contains theorems and definitions for Z group.

groups.v:

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.

groups_Z.v:

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.

The attempt to define pow_z fails with message:

The term "pow a (Pos.to_nat x)" has type "groups.G" while it is expected to have type "G".

If we use the different signature: Definition pow_z (a: G) (z: Z) : G

instead of Definition pow_z (a: groups.G) (z: Z) : G.

then it gives another error:

The term "a" has type "G" while it is expected to have type "groups.G".

How to fix this?

question from:https://stackoverflow.com/questions/65908229/error-when-referencing-type-variable-from-another-file

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

In Coq, the command Parameter G : Type declares a global constant, which is akin to axiomatizing the existence of an abstract Type G : Type. From a theoretical point of view, this should be ok as this axiom is trivially realizable, but I think you meant Variable G : Type to denote a local variable instead.

The errors messages of Coq follow from there because you declare two global constants named G, one in each module. As soon as the second one is declared, the first one is designated by groups.G by Coq (it's the shortest name that disambiguates this constant from others). Now pow operates on and returns a groups.G, while you require pow_z returns a G (which in file groups_Z.v at this location means groups_Z.G, and is different from groups.G).

NB: Group theory has been developed several times in Coq, and if you want to do anything else than experimenting with the system, I would advise you work on top of existing libraries. For example the mathematical components library has a finite group library.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...