Section ClosureRelations.
Variables (X: Type).
Implicit Types (R S: X -> X -> Prop) (x y z : X).
Notation "R <<= S" := (subrelation R S) (at level 70).
Notation "R === S" := (R <<= S /\ S <<= R) (at level 70).
Definition functional R :=
forall x y z, R x y -> R x z -> y = z.
Inductive star R : X -> X -> Prop :=
| starRefl x     : star R x x
| starStep x x' y : R x x' -> star R x' y -> star R x y.
Inductive multiple R : X -> X -> Prop :=
| multipleSingle x y: R x y -> multiple R x y
| multipleStep x x' y: R x x' -> multiple R x' y -> multiple R x y.
Inductive counted R : nat -> X -> X -> Prop :=
| countedRefl x: counted R 0 x x
| countedStep x x' y n: R x x' -> counted R n x' y -> counted R (S n) x y.
Inductive sym R: X -> X -> Prop :=
| symId x y: R x y -> sym R x y
| symInv x y: R y x -> sym R x y.
Hint Constructors star multiple counted : core.
Definition Normal R x := forall y, ~ R x y.
Definition evaluates R s t := star R s t /\ Normal R t.
Definition equiv R := star (sym R).
Fact Normal_star_stops R x:
Normal R x -> forall y, star R x y -> x = y.
Fact counted_trans R x y z m n:
counted R m x y -> counted R n y z -> counted R (m + n) x z.
Global Instance multiple_transitive R:
Transitive (multiple R).
Global Instance star_preorder R: PreOrder (star R).
Global Instance star_exp R:
R <<= star R.
Global Instance multiple_exp R:
R <<= multiple R.
Fact counted_exp R:
R === counted R 1.
Global Instance multiple_star R : multiple R <<= star R.

Lemma multiple_destruct R x y:
multiple R x y <-> exists2 x', (R x x') & (star R x' y).