Library finiteness

Require Import base.
Require Import prelim.

Definition prefinite A (P:A -> Prop) :=
  exists l, forall x:A, P x -> In x l.

Definition finite A (P:A -> Prop) :=
  exists l, forall x:A, P x <-> In x l.

Lemma finite_prefinite : forall A P,
  finite A P -> prefinite A P.

Lemma finite_pairs A B PA PB :
  finite A PA -> finite B PB ->
  finite (A * B) (fun x => PA (fst x) /\ PB (snd x)).

Lemma finite_lists_length_n A PA : forall n,
  finite A PA ->
  finite (list A) (fun l => (forall x, In x l -> PA x) /\ length l <= n).

Lemma nodup_list_length : forall A (l l':list A),
  (forall x, In x l' -> In x l) ->
  NoDup l' -> length l' <= length l.

Lemma finite_nodup_lists A PA :
  finite A PA ->
  prefinite (list A) (fun l => (forall x, In x l -> PA x) /\ NoDup l).

Lemma finite_select {Classic:EM} : forall A (PA PA':A -> Prop),
  (forall x, PA' x -> PA x) ->
  prefinite A PA ->
  finite A PA'.

Lemma finite_transform :
  forall A B (PA:A->Prop) (PB:B->Prop) (R: A -> B -> Prop),
  (forall a, PA a -> exists! b, R a b /\ PB b) ->
  (forall b, PB b -> exists a, R a b /\ PA a) ->
  finite A PA -> finite B PB.

Lemma finite_mapping : forall A PA B PB,
  finite A PA ->
  (forall a, PA a -> finite B (PB a)) ->
  finite (A * B) (fun x => PA (fst x) /\ PB (fst x) (snd x)).