bedrock.prelude.sets
(*
* Copyright (C) BedRock Systems Inc. 2021
*
* This software is distributed under the terms of the BedRock Open-Source License.
* See the LICENSE-BedRock file in the repository root for details.
*)
Require Export stdpp.sets.
Require Import bedrock.prelude.base.
* Copyright (C) BedRock Systems Inc. 2021
*
* This software is distributed under the terms of the BedRock Open-Source License.
* See the LICENSE-BedRock file in the repository root for details.
*)
Require Export stdpp.sets.
Require Import bedrock.prelude.base.
high cost supports specialization Leibniz equality here is fine for all finite sets, coPset, and
coGset. We could presumably generalize to setoid equivalence.
fun Xs Ys => set_Forall (fun X => set_Forall (fun Y => X = Y \/ X ## Y) Ys) Xs.
#[global] Instance set_pairwise_disjoint_symmetric
`{ElemOf C D, Disjoint C, !Symmetric (##@{C})} :
Symmetric (##ₚ@{D}) | 100.
#[global] Instance set_pairwise_disjoint_symmetric
`{ElemOf C D, Disjoint C, !Symmetric (##@{C})} :
Symmetric (##ₚ@{D}) | 100.
high cost supports specialization
Proof. intros ?? HD ? HY ? HX. destruct (HD _ HX _ HY). by left. by right. Qed.
Section semi_set.
#[local] Set Default Proof Using "Type*".
Context `{SemiSet A C}.
Implicit Types X Y : C.
Section semi_set.
#[local] Set Default Proof Using "Type*".
Context `{SemiSet A C}.
Implicit Types X Y : C.
Witnesses for disjoint semisets
Lemma set_disjoint_not_Forall_1 X Y : X ## Y <-> set_Forall (.∉ Y) X.
Proof. done. Qed.
Lemma set_disjoint_not_Forall_2 X Y : X ## Y <-> set_Forall (.∉ X) Y.
Proof. by rewrite [X ## Y]symmetry_iff. Qed.
(* More convenient for rewriting than set_Forall_union_inv_1, set_Forall_union_inv_2, set_Forall_union. *)
Lemma set_Forall_union_equiv (P : A → Prop) X Y :
set_Forall P (X ∪ Y) ↔ set_Forall P X ∧ set_Forall P Y.
Proof. unfold set_Forall. set_solver. Qed.
End semi_set.
Proof. done. Qed.
Lemma set_disjoint_not_Forall_2 X Y : X ## Y <-> set_Forall (.∉ X) Y.
Proof. by rewrite [X ## Y]symmetry_iff. Qed.
(* More convenient for rewriting than set_Forall_union_inv_1, set_Forall_union_inv_2, set_Forall_union. *)
Lemma set_Forall_union_equiv (P : A → Prop) X Y :
set_Forall P (X ∪ Y) ↔ set_Forall P X ∧ set_Forall P Y.
Proof. unfold set_Forall. set_solver. Qed.
End semi_set.
Pairwise disjointness for SemiSet
Section semi_set.
#[local] Set Default Proof Using "Type*".
Context `{SemiSet C D, Disjoint C}.
Implicit Types X Y : C.
Implicit Types Xs Ys : D.
Lemma pairwise_disjoint_singleton X : [##ₚ@{D} {[X]}].
Proof.
rewrite/pairwise_disjoint/set_pairwise_disjoint.
rewrite !set_Forall_singleton. by left.
Qed.
Lemma pairwise_disjoint_union_1 Xs Ys :
[##ₚ Xs ∪ Ys] -> [##ₚ Xs] /\ [##ₚ Ys] /\ Xs ##ₚ Ys.
Proof.
intros HD. split_and?.
- apply (set_Forall_union_inv_1 _ _ Ys)=>X /HD. by apply set_Forall_union_inv_1.
- apply (set_Forall_union_inv_2 _ Xs)=>X /HD. by apply set_Forall_union_inv_2.
- apply (set_Forall_union_inv_1 _ _ Ys)=>X /HD. by apply set_Forall_union_inv_2.
Qed.
Lemma pairwise_disjoint_union_2 `{!Symmetric (##@{C})} Xs Ys :
[##ₚ Xs] -> [##ₚ Ys] -> Xs ##ₚ Ys -> [##ₚ Xs ∪ Ys].
Proof.
intros HXs HYs HXYs. apply set_Forall_union=>X HX; apply set_Forall_union=>Y HY.
- exact: HXs.
- exact: HXYs.
- apply symmetry in HXYs. exact: HXYs.
- exact: HYs.
Qed.
Lemma pairwise_disjoint_union `{!Symmetric (##@{C})} Xs Ys :
[##ₚ Xs ∪ Ys] <-> [##ₚ Xs] /\ [##ₚ Ys] /\ Xs ##ₚ Ys.
Proof.
split.
- by apply pairwise_disjoint_union_1.
- intros (? & ? & ?). by apply pairwise_disjoint_union_2.
Qed.
End semi_set.
#[global] Hint Resolve pairwise_disjoint_union_2 : core.
Section top_set.
Context `{TopSet A C}.
Implicit Types x y : A.
Implicit Types X Y : C.
#[local] Set Default Proof Using "Type*".
(* Named after union_empty_l (+ missing top_set_ prefix) *)
#[global] Instance top_set_intersection_top_l : LeftId (≡@{C}) ⊤ (∩).
Proof. intros ?. set_solver. Qed.
#[global] Instance top_set_intersection_top_r : RightId (≡@{C}) ⊤ (∩).
Proof. intros ?. set_solver. Qed.
Section leibniz.
Context `{!LeibnizEquiv C}.
#[global] Instance top_set_intersection_top_l_L : LeftId (=@{C}) ⊤ (∩).
Proof. intros ?. unfold_leibniz. apply (left_id _ _). Qed.
#[global] Instance top_set_intersection_top_r_L : RightId (=@{C}) ⊤ (∩).
Proof. intros ?. unfold_leibniz. apply (right_id _ _). Qed.
End leibniz.
End top_set.
Lemma union_minus_l `{Set_ A C} (X Y : C) : (X ∪ Y) ∖ X ≡ Y ∖ X.
Proof. set_solver. Qed.
Lemma union_minus_l_L `{Set_ A C, !LeibnizEquiv C} (X Y : C) : (X ∪ Y) ∖ X = Y ∖ X.
Proof. set_solver. Qed.
Lemma union_minus_r `{Set_ A C} (X Y : C) : (X ∪ Y) ∖ Y ≡ X ∖ Y.
Proof. set_solver. Qed.
Lemma union_minus_r_L `{Set_ A C, !LeibnizEquiv C} (X Y : C) : (X ∪ Y) ∖ Y = X ∖ Y.
Proof. set_solver. Qed.
#[local] Set Default Proof Using "Type*".
Context `{SemiSet C D, Disjoint C}.
Implicit Types X Y : C.
Implicit Types Xs Ys : D.
Lemma pairwise_disjoint_singleton X : [##ₚ@{D} {[X]}].
Proof.
rewrite/pairwise_disjoint/set_pairwise_disjoint.
rewrite !set_Forall_singleton. by left.
Qed.
Lemma pairwise_disjoint_union_1 Xs Ys :
[##ₚ Xs ∪ Ys] -> [##ₚ Xs] /\ [##ₚ Ys] /\ Xs ##ₚ Ys.
Proof.
intros HD. split_and?.
- apply (set_Forall_union_inv_1 _ _ Ys)=>X /HD. by apply set_Forall_union_inv_1.
- apply (set_Forall_union_inv_2 _ Xs)=>X /HD. by apply set_Forall_union_inv_2.
- apply (set_Forall_union_inv_1 _ _ Ys)=>X /HD. by apply set_Forall_union_inv_2.
Qed.
Lemma pairwise_disjoint_union_2 `{!Symmetric (##@{C})} Xs Ys :
[##ₚ Xs] -> [##ₚ Ys] -> Xs ##ₚ Ys -> [##ₚ Xs ∪ Ys].
Proof.
intros HXs HYs HXYs. apply set_Forall_union=>X HX; apply set_Forall_union=>Y HY.
- exact: HXs.
- exact: HXYs.
- apply symmetry in HXYs. exact: HXYs.
- exact: HYs.
Qed.
Lemma pairwise_disjoint_union `{!Symmetric (##@{C})} Xs Ys :
[##ₚ Xs ∪ Ys] <-> [##ₚ Xs] /\ [##ₚ Ys] /\ Xs ##ₚ Ys.
Proof.
split.
- by apply pairwise_disjoint_union_1.
- intros (? & ? & ?). by apply pairwise_disjoint_union_2.
Qed.
End semi_set.
#[global] Hint Resolve pairwise_disjoint_union_2 : core.
Section top_set.
Context `{TopSet A C}.
Implicit Types x y : A.
Implicit Types X Y : C.
#[local] Set Default Proof Using "Type*".
(* Named after union_empty_l (+ missing top_set_ prefix) *)
#[global] Instance top_set_intersection_top_l : LeftId (≡@{C}) ⊤ (∩).
Proof. intros ?. set_solver. Qed.
#[global] Instance top_set_intersection_top_r : RightId (≡@{C}) ⊤ (∩).
Proof. intros ?. set_solver. Qed.
Section leibniz.
Context `{!LeibnizEquiv C}.
#[global] Instance top_set_intersection_top_l_L : LeftId (=@{C}) ⊤ (∩).
Proof. intros ?. unfold_leibniz. apply (left_id _ _). Qed.
#[global] Instance top_set_intersection_top_r_L : RightId (=@{C}) ⊤ (∩).
Proof. intros ?. unfold_leibniz. apply (right_id _ _). Qed.
End leibniz.
End top_set.
Lemma union_minus_l `{Set_ A C} (X Y : C) : (X ∪ Y) ∖ X ≡ Y ∖ X.
Proof. set_solver. Qed.
Lemma union_minus_l_L `{Set_ A C, !LeibnizEquiv C} (X Y : C) : (X ∪ Y) ∖ X = Y ∖ X.
Proof. set_solver. Qed.
Lemma union_minus_r `{Set_ A C} (X Y : C) : (X ∪ Y) ∖ Y ≡ X ∖ Y.
Proof. set_solver. Qed.
Lemma union_minus_r_L `{Set_ A C, !LeibnizEquiv C} (X Y : C) : (X ∪ Y) ∖ Y = X ∖ Y.
Proof. set_solver. Qed.