Fixpoint Map_of_alist (l:alist) : Map A :=
    match l with
    | nil => M0 A
    | (a, y) :: l' => MapPut A (Map_of_alist l') a y
    end.

(* Specifications: *)
Lemma Map_of_alist_semantics : forall l:alist, eqm A (alist_semantics l) (MapGet A (Map_of_alist l)).
Lemma Map_of_alist_of_Map : forall m:Map A, eqmap A (Map_of_alist (alist_of_Map m)) m.
Lemma alist_of_Map_of_alist : forall l:alist, eqm A (alist_semantics (alist_of_Map (Map_of_alist l))) (alist_semantics l).
Lemma fold_right_aapp : forall (M:Type) (neutral:M) (op:M -> M -> M), (forall a b c:M, op (op a b) c = op a (op b c)) -> (forall a:M, op neutral a = a) -> forall (f:ad -> A -> M) (l l':alist), fold_right (fun (r:ad * A) (m:M) => let (a, y) := r in op (f a y) m) neutral (aapp l l') = op (fold_right (fun (r:ad * A) (m:M) => let (a, y) := r in op (f a y) m) neutral l) (fold_right (fun (r:ad * A) (m:M) => let (a, y) := r in op (f a y) m) neutral l').
Lemma MapFold_as_fold_1 : forall (M:Type) (neutral:M) (op:M -> M -> M), (forall a b c:M, op (op a b) c = op a (op b c)) -> (forall a:M, op neutral a = a) -> (forall a:M, op a neutral = a) -> forall (f:ad -> A -> M) (m:Map A) (pf:ad -> ad), MapFold1 M neutral op f pf m = fold_right (fun (r:ad * A) (m:M) => let (a, y) := r in op (f a y) m) neutral (MapFold1 alist anil aapp (fun (a:ad) (y:A) => acons (a, y) anil) pf m).
Lemma MapFold_as_fold : forall (M:Type) (neutral:M) (op:M -> M -> M), (forall a b c:M, op (op a b) c = op a (op b c)) -> (forall a:M, op neutral a = a) -> (forall a:M, op a neutral = a) -> forall (f:ad -> A -> M) (m:Map A), MapFold M neutral op f m = fold_right (fun (r:ad * A) (m:M) => let (a, y) := r in op (f a y) m) neutral (alist_of_Map m).
Lemma alist_MapMerge_semantics : forall m m':Map A, eqm A (alist_semantics (aapp (alist_of_Map m') (alist_of_Map m))) (alist_semantics (alist_of_Map (MapMerge A m m'))).
Lemma alist_MapMerge_semantics_disjoint : forall m m':Map A, eqmap A (MapDomRestrTo A A m m') (M0 A) -> eqm A (alist_semantics (aapp (alist_of_Map m) (alist_of_Map m'))) (alist_semantics (alist_of_Map (MapMerge A m m'))).
Lemma alist_semantics_disjoint_comm : forall l l':alist, eqmap A (MapDomRestrTo A A (Map_of_alist l) (Map_of_alist l')) (M0 A) -> eqm A (alist_semantics (aapp l l')) (alist_semantics (aapp l' l)).