(*									*)
(*  On va definir de meme la notion de chemin sur un automate		*)
(*  asynchrone en rajoutant les transitions par epsilon.		*)
(*									*)

Inductive chemin_A (q d : Ensf) : Elt -> Elt -> Word -> Prop :=
  | chemin_A_nil :
      forall e1 e2 : Elt,
      dans e1 q -> e1 = e2 :>Elt -> chemin_A q d e1 e2 nil
  | chemin_A_cons :
      forall (e1 e e2 x : Elt) (w : Word),
      chemin_A q d e e2 w ->
      dans e1 q ->
      dans x alph ->
      dans (couple e1 (couple x e)) d -> chemin_A q d e1 e2 (cons x w)
  | chemin_A_epsilon :
      forall (e1 e e2 : Elt) (w : Word),
      chemin_A q d e e2 w ->
      dans e1 q ->
      dans (couple e1 (couple epsilon e)) d -> chemin_A q d e1 e2 w.(*									*)
(*  On va definir de meme la notion de chemin sur un automate		*)
(*  asynchrone en rajoutant les transitions par epsilon.		*)
(*									*)

Inductive chemin_A (q d : Ensf) : Elt -> Elt -> Word -> Prop :=
  | chemin_A_nil :
      forall e1 e2 : Elt,
      dans e1 q -> e1 = e2 :>Elt -> chemin_A q d e1 e2 nil
  | chemin_A_cons :
      forall (e1 e e2 x : Elt) (w : Word),
      chemin_A q d e e2 w ->
      dans e1 q ->
      dans x alph ->
      dans (couple e1 (couple x e)) d -> chemin_A q d e1 e2 (cons x w)
  | chemin_A_epsilon :
      forall (e1 e e2 : Elt) (w : Word),
      chemin_A q d e e2 w ->
      dans e1 q ->
      dans (couple e1 (couple epsilon e)) d -> chemin_A q d e1 e2 w.(*									*)
(*  On va definir de meme la notion de chemin sur un automate		*)
(*  asynchrone en rajoutant les transitions par epsilon.		*)
(*									*)

Inductive chemin_A (q d : Ensf) : Elt -> Elt -> Word -> Prop :=
  | chemin_A_nil :
      forall e1 e2 : Elt,
      dans e1 q -> e1 = e2 :>Elt -> chemin_A q d e1 e2 nil
  | chemin_A_cons :
      forall (e1 e e2 x : Elt) (w : Word),
      chemin_A q d e e2 w ->
      dans e1 q ->
      dans x alph ->
      dans (couple e1 (couple x e)) d -> chemin_A q d e1 e2 (cons x w)
  | chemin_A_epsilon :
      forall (e1 e e2 : Elt) (w : Word),
      chemin_A q d e e2 w ->
      dans e1 q ->
      dans (couple e1 (couple epsilon e)) d -> chemin_A q d e1 e2 w.(*									*)
(*  On va definir de meme la notion de chemin sur un automate		*)
(*  asynchrone en rajoutant les transitions par epsilon.		*)
(*									*)

Inductive chemin_A (q d : Ensf) : Elt -> Elt -> Word -> Prop :=
  | chemin_A_nil :
      forall e1 e2 : Elt,
      dans e1 q -> e1 = e2 :>Elt -> chemin_A q d e1 e2 nil
  | chemin_A_cons :
      forall (e1 e e2 x : Elt) (w : Word),
      chemin_A q d e e2 w ->
      dans e1 q ->
      dans x alph ->
      dans (couple e1 (couple x e)) d -> chemin_A q d e1 e2 (cons x w)
  | chemin_A_epsilon :
      forall (e1 e e2 : Elt) (w : Word),
      chemin_A q d e e2 w ->
      dans e1 q ->
      dans (couple e1 (couple epsilon e)) d -> chemin_A q d e1 e2 w.(*  Inversion de la definition...					*)

Definition Chemin_A (q d : Ensf) (e1 e2 : Elt) (w : Word) : Prop :=
  match w return Prop with
  | nil =>
      (* nil  *) 
      dans e1 q /\ e1 = e2 :>Elt \/
      (exists e : Elt,
         chemin_A q d e e2 nil /\
         dans e1 q /\ dans (couple e1 (couple epsilon e)) d)
      
      (* cons *) 
  | cons a w =>
      (exists e : Elt,
         chemin_A q d e e2 w /\
         dans e1 q /\ dans a alph /\ dans (couple e1 (couple a e)) d) \/
      (exists e : Elt,
         chemin_A q d e e2 w /\
         dans e1 q /\ dans (couple e1 (couple epsilon e)) d)
  end.

(* Specifications: *)
Lemma chemin_A_d1_d2 : forall (q d1 d2 : Ensf) (w : Word) (e1 e2 : Elt), chemin_A q d1 e1 e2 w -> inclus d1 d2 -> chemin_A q d2 e1 e2 w.
Lemma chemin_A_q1_q2 : forall (q1 q2 d : Ensf) (e1 e2 : Elt) (w : Word), chemin_A q1 d e1 e2 w -> inclus q1 q2 -> chemin_A q2 d e1 e2 w.
Lemma chemin_chemin_A : forall (q d : Ensf) (w : Word) (e1 e2 : Elt), chemin e1 e2 q d w -> chemin_A q d e1 e2 w.
Lemma chemin_Append : forall (e1 e e2 : Elt) (q d : Ensf) (w1 w2 : Word), chemin_A q d e1 e w1 -> chemin_A q d e e2 w2 -> chemin_A q d e1 e2 (Append w1 w2).
Lemma dansA_e1_q : forall (q d : Ensf) (w : Word) (e1 e2 : Elt), chemin_A q d e1 e2 w -> dans e1 q.
Lemma dansA_e2_q : forall (q d : Ensf) (w : Word) (e1 e2 : Elt), chemin_A q d e1 e2 w -> dans e2 q.
Lemma cheminA_monoid : forall (w : Word) (q qd qaA dA : Ensf), automate_A q qd qaA dA -> forall e1 e2 : Elt, chemin_A q dA e1 e2 w -> inmonoid alph w.