Require Export Ensembles.
Require Export Image.
Require Export Finite_sets.
Require Export FunctionProperties.
Set Asymmetric Patterns.
Inductive FiniteT : Type -> Prop :=
| empty_finite: FiniteT False
| add_finite: forall T:Type, FiniteT T -> FiniteT (option T)
| bij_finite: forall (X Y:Type) (f:X->Y), FiniteT X ->
invertible f -> FiniteT Y.
Definition FiniteT_nat_cardinal (X:Type) (H:FiniteT X) : nat :=
proj1_sig (constructive_definite_description _
(FiniteT_has_nat_cardinal X H)).

Lemma unique_FiniteT_nat_cardinal:
exists! f: (forall (X:Type), FiniteT X -> nat),
f False empty_finite = 0 /\
(forall (X:Type) (H:FiniteT X),
f (option X) (add_finite X H) = S (f X H)) /\
(forall (X Y:Type) (H:FiniteT X) (g:X->Y) (Hinv:invertible g),
f Y (bij_finite X Y g H Hinv) = f X H).