Tactic Notation "env" "induction" ident(E) :=
try (intros until E);
let T := type of E in
let T := eval compute in T in
match T with
| list (?key * ?A) => induction E using (alist_ind A)
end.
Tactic Notation "env" "induction" ident(E) "as" simple_intropattern(P) :=
try (intros until E);
let T := type of E in
let T := eval compute in T in
match T with
| list (?key * ?A) => induction E as P using (alist_ind A)
end.
(* *********************************************************************** *)
(** * Basic facts about [disjoint] *)
Section Disjoint.
Implicit Types A B C : Type.

Axiom disjoint_cons_r :
forall A B x a (E : list (atom*A)) (F : list (atom*B)),
disjoint F ((x, a) :: E) <-> ~ In x (dom F) /\ disjoint E F.