Section ep_quotient.
Variable (X : Type) (R : X -> X -> Prop) (f : nat -> option X)
(Hf : forall x, exists y n, f n = Some y /\ R y x).
Hypothesis HR1 : equiv _ R.
Hypothesis HR2 : dec R.
Let T n m :=
match f n, f m with
| Some x, Some y => R x y
| None  , None   => True
| _     , _      => False
end.
Let HT1 : equiv _ T.
Infix "≈" := T (at level 70, no associativity).
Let is_repr x n :=
match f n with
| Some r => R r x
| None   => False
end.
Let is_repr_trans x1 x2 n : R x1 x2 -> is_repr x1 n -> is_repr x2 n.
Let is_repr_dec : dec is_repr.
Let is_repr_exists x : ex (is_repr x).
Let is_min_repr x n :=
is_repr x n /\ forall m, is_repr x m -> n <= m.
Let is_min_repr_inj x n1 n2 : is_min_repr x n1 -> is_min_repr x n2 -> n1 = n2.
Let is_min_repr_involutive x n : is_min_repr x n ->
match f n with
| Some y => is_min_repr y n
| None   => False
end.
Let find_min_repr x : sig (is_min_repr x).
Let is_min_repr_dec : dec is_min_repr.
Let P n :=
match f n with
| Some x => if is_min_repr_dec x n then true else false
| None   => false
end.
Let P_spec n : P n = true <-> exists x, f n = Some x /\ is_min_repr x n.
Let Y := sig (fun x => P x = true).
Let pi1_inj : forall x y : Y, proj1_sig x = proj1_sig y -> x = y.
Let Y_discrete : dec (@eq Y).
Let is_min_repr_P n x : is_min_repr x n -> P n = true.
Let cls (x : X) : Y.
Let rpr (y : Y) := proj1_sig (P_to_X _ (proj2_sig y)).
Let Hrpr y : f (proj1_sig y) = Some (rpr y).
Let Hrc x1 x2 : R x1 x2 <-> cls x1 = cls x2.
Local Fact enum_quotient_rec :
{ Y : Type & { _ : dec (@eq Y) & quotient R Y } }.
End ep_quotient.
(* Given type X with a decidable equivalence ~ over X such that the classes of X/~ can be enumerated then one can build the quotient X/~ into a discrete type Y and Y is necessarily enumerated, see below *)

Theorem enum_quotient X R :
nat_enum_cls R
-> equiv X R
-> dec R
-> { Y : Type & { _ : dec (@eq Y) & quotient R Y } }.