Library Zmod


Require Import ZArith.
Require Import Coq.Sets.Ensembles.
Require Import Coq.Arith.Euclid.


Require Import Zfacts.
Require Import EnsembleFacts.

Open Local Scope Z_scope.

Section Zmod.

Definition Zmodequiv (a b N:Z) :Prop := exists k, a-b=k*N.

Parameter ZmodN : Z->Type.
Parameter Zmod : forall (N a:Z), ZmodN N.



Axiom Zmodequivalence_right: forall a b N:Z,
Zmodequiv a b N -> Zmod N a=Zmod N b.
Axiom Zmodequivalence_left: forall a b N:Z,
Zmod N a=Zmod N b -> Zmodequiv a b N.

Axiom Zmod_elim : forall (N:Z) (a:ZmodN N),
exists b:Z, Zmod N b=a.

Theorem Zmod_addition : forall (N a b c:Z),
 (Zmod N a)=(Zmod N b)->(Zmod N (a +c))=(Zmod N (b+c)).

Theorem Zmod_opp : forall (N a b:Z),
 (Zmod N a)=(Zmod N b)->(Zmod N (-a))=(Zmod N (-b)).

Parameter Zmod_add :
forall N:Z,(ZmodN N)->(ZmodN N)->(ZmodN N).

Axiom Zmod_add_Z: forall (N aZ bZ:Z) (a b:ZmodN N),
a=Zmod N aZ -> b=Zmod N bZ ->
 Zmod_add N a b=Zmod N (aZ+bZ).

Definition Zmod_repset (N:Z) (R:Ensemble Z):Prop:=
(forall a:ZmodN N,exists r:Z, Zmod N r=a /\ In Z R r)
/\
(forall r s:Z, In Z R r-> In Z R s-> s<>r
 -> Zmod N r<>Zmod N s).

Definition Zmod_repsetnat (N:Z) (R:Ensemble nat):Prop:=
(forall a:ZmodN N,exists r:nat, Zmod N (Z_of_nat r)=a
  /\ In nat R r)
/\
(forall r s:nat, In nat R r-> In nat R s-> s<>r
 -> Zmod N (Z_of_nat r)<>Zmod N (Z_of_nat s)).

Lemma Zmod_haspos : forall (N:Z) (a:ZmodN N), N>0->
exists n:Z, n>=0 /\ Zmod N n=a.

Theorem Zmod_canonical : forall (N:Z) (a:ZmodN N), N>0->
exists n:Z, 0<=n<N /\ Zmod N n=a.

Theorem Zmod_nat_repsetnat : forall (N:Z), N>0->
Zmod_repsetnat N (nat_firsts (Zabs_nat N)).

Theorem Zmod_addisbijection : forall (N:Z) (a:ZmodN N),
Bijective (ZmodN N) (ZmodN N) (fun x:ZmodN N=>Zmod_add N x a).




Theorem Zmodeg_equiv7_1_8 : Zmod 7 1=Zmod 7 8.

Theorem Zmodeg_add10_1_8 :
Zmod_add 10 (Zmod 10 1) (Zmod 10 8)=Zmod 10 9.

Print Zind.
Theorem Zmodeg_parity : forall a:ZmodN 2,
a=Zmod 2 0 \/ a=Zmod 2 1.
Print Zmod_elim.



Qed.

End Zmod.