From Undecidability.Shared.Libs.PSL Require Export Prelim EqDec.
Export ListNotations.
Notation "x 'el' A" := (In x A) (at level 70).
Notation "A <<= B" := (incl A B) (at level 70).
Notation "| A |" := (length A) (at level 65).
Definition equi X (A B : list X) : Prop := incl A B /\ incl B A.
Notation "A === B" := (equi A B) (at level 70).
Hint Unfold equi : core.
Hint Extern 4 =>
match goal with
|[ H: ?x el nil |- _ ] => destruct H
end : core.
(* ** Lists *)
(* Register additional simplification rules with autorewrite / simpl_list *)
(* Print Rewrite HintDb list. *)
Hint Rewrite <- app_assoc : list.
Hint Rewrite rev_app_distr map_app prod_length : list.
(* *** Decisions for lists *)
Instance list_in_dec X (x : X) (A : list X) :
eq_dec X -> dec (x el A).
(* Certifying find *)
Arguments cfind {X} A p {p_dec}.
Instance list_forall_dec X A (p : X -> Prop) :
(forall x, dec (p x)) -> dec (forall x, x el A -> p x).
Instance list_exists_dec X A (p : X -> Prop) :
(forall x, dec (p x)) -> dec (exists x, x el A /\ p x).

Lemma list_exists_DM X A  (p : X -> Prop) :
(forall x, dec (p x)) ->
~ (forall x, x el A -> ~ p x) -> exists x, x el A /\ p x.