(*========================================================== VERSION AUGUST 08  TOPOLOGICAL FMAPS, HMAPS -  WITH TAGS AND EMBEDDINGS  PART 2 : SETS OF DARTS, PATHS, ORBITS  WITH NOETHERIAN INDUCTION ON A BIJECTION f WITH SIGNATURES AND MODULES  VERSION WITH set AND card: OK  NEW VERSION, COMPLETED WITH DIRECT period, REULTS ABOUT orbits AND rem: OK (August 2008) ============================================================*)
Require Export Jordan1.
Require Euclid.
Require Compare.
Require Recdef.
Require Arith.
(*========================================================= SETS OF DARTS  FOR NOETHERIAN INDUCTIVE REASONINGS ==========================================================*)
Inductive set:Set:=
Vs : set | Is : set -> dart -> set.
Fixpoint exds(s:set)(z:dart){struct s}:Prop:=
match s with
Vs => False
| Is s0 x => x=z \/ exds s0 z
end.
(* IF NO DART IS IN s, s IS Vs: *)
(* SUPPRESSION OF ALL OCCURRENCES of z: *)
Fixpoint Ds(s:set)(z:dart){struct s}:set:=
match s with
Vs => Vs
| Is s0 x =>
if eq_dart_dec x z then (Ds s0 z)
else Is (Ds s0 z) x
end.
induction s.
simpl in |- *.
tauto.
simpl in |- *.
intros x z.
elim (eq_dart_dec d x).
intro.
apply IHs.
simpl in |- *.
intros.
elim H.
intro.
rewrite <- H0.
intro.
rewrite H1 in b.
tauto.
apply IHs.
Qed.
(* "cardinal" of a (multi-)set: *)
Fixpoint card(s:set):nat:=
match s with
Vs => 0%nat
| Is s0 x =>
if exds_dec s0 x then card s0
else (1 + card s0)%nat
end.
(* ========================================================== RELATIONSHIPS BETWEEN sets AND fmaps ===========================================================*)
(* fmap to set *)
Fixpoint fmap_to_set(m:fmap):set:=
match m with
V => Vs
| I m0 x _ _ => Is (fmap_to_set m0) x
| L m0 _ _ _ => (fmap_to_set m0)
end.
Fixpoint ndN (m:fmap):nat:=
match m with
V => 0%nat
| I m0 x _ _ =>
if exd_dec m0 x then ndN m0
else (1 + ndN m0)%nat
| L m0 _ _ _ => ndN m0
end.
(* ======================================================== ALWAYS (multi-)sets ==========================================================*)
(* s1 - s2: *)
Fixpoint set_minus(s1 s2:set){struct s1}:set:=
match s1 with
Vs => Vs
| Is s0 x =>
if exds_dec s2 x then set_minus s0 s2
else Is (set_minus s0 s2) x
end.

Lemma exds_set_minus_eq:forall(s1 s2:set)(z:dart),
(exds s1 z /\ ~exds s2 z) <-> exds (set_minus s1 s2) z.