l3lab/ntp-mathlib huggingface dataset:
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.supClosure (hs : s.Finite) : (supClosure s).Finite := by
  lift s to Finset α using hs
  

Proof state:
case intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeSup α
inst✝ : SemilatticeSup β
t : Set α
a b : α
s : Finset α
⊢ Set.Finite (supClosure ↑s)

Next tactic:
classical
  refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.sup' (mem_filter.1 t.2).2 id).finite_toSet.subset _
  rintro _ ⟨t, ht, hts, rfl⟩
  simp only [id_eq, coe_image, mem_image, mem_coe, mem_attach, true_and, Subtype.exists,
    Finset.mem_powerset, Finset.not_nonempty_iff_eq_empty, mem_filter]
  exact ⟨t, ⟨hts, ht⟩, rfl⟩
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.supClosure (hs : s.Finite) : (supClosure s).Finite := by
  lift s to Finset α using hs
  classical
  

Proof state:
case intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeSup α
inst✝ : SemilatticeSup β
t : Set α
a b : α
s : Finset α
⊢ Set.Finite (supClosure ↑s)

Next tactic:
refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.sup' (mem_filter.1 t.2).2 id).finite_toSet.subset _
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.supClosure (hs : s.Finite) : (supClosure s).Finite := by
  lift s to Finset α using hs
  classical
  refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.sup' (mem_filter.1 t.2).2 id).finite_toSet.subset _
  

Proof state:
case intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeSup α
inst✝ : SemilatticeSup β
t : Set α
a b : α
s : Finset α
⊢ supClosure ↑s ⊆
    ↑(Finset.image (fun t => sup' ↑t (_ : Finset.Nonempty ↑t) id) (attach (filter Finset.Nonempty (Finset.powerset s))))

Next tactic:
rintro _ ⟨t, ht, hts, rfl⟩
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.supClosure (hs : s.Finite) : (supClosure s).Finite := by
  lift s to Finset α using hs
  classical
  refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.sup' (mem_filter.1 t.2).2 id).finite_toSet.subset _
  rintro _ ⟨t, ht, hts, rfl⟩
  

Proof state:
case intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeSup α
inst✝ : SemilatticeSup β
t✝ : Set α
a b : α
s t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ ↑s
⊢ sup' t ht id ∈
    ↑(Finset.image (fun t => sup' ↑t (_ : Finset.Nonempty ↑t) id) (attach (filter Finset.Nonempty (Finset.powerset s))))

Next tactic:
simp only [id_eq, coe_image, mem_image, mem_coe, mem_attach, true_and, Subtype.exists,
    Finset.mem_powerset, Finset.not_nonempty_iff_eq_empty, mem_filter]
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.supClosure (hs : s.Finite) : (supClosure s).Finite := by
  lift s to Finset α using hs
  classical
  refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.sup' (mem_filter.1 t.2).2 id).finite_toSet.subset _
  rintro _ ⟨t, ht, hts, rfl⟩
  simp only [id_eq, coe_image, mem_image, mem_coe, mem_attach, true_and, Subtype.exists,
    Finset.mem_powerset, Finset.not_nonempty_iff_eq_empty, mem_filter]
  

Proof state:
case intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeSup α
inst✝ : SemilatticeSup β
t✝ : Set α
a b : α
s t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ ↑s
⊢ ∃ a,
    ∃ (h : a ⊆ s ∧ Finset.Nonempty a),
      (sup' a (_ : Finset.Nonempty ↑{ val := a, property := (_ : a ∈ filter Finset.Nonempty (Finset.powerset s)) })
          fun x => x) =
        sup' t (_ : Finset.Nonempty t) fun x => x

Next tactic:
exact ⟨t, ⟨hts, ht⟩, rfl⟩
/-- Every set in a join-semilattice generates a set closed under join. -/
@[simps! isClosed]
def infClosure : ClosureOperator (Set α) := ClosureOperator.ofPred
  (λ s ↦ {a | ∃ (t : Finset α) (ht : t.Nonempty), ↑t ⊆ s ∧ t.inf' ht id = a})
  InfClosed
  (λ s a ha ↦ ⟨{a}, singleton_nonempty _, by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s✝ t : Set α
a✝ b : α
s : Set α
a : α
ha : a ∈ s
⊢ ↑{a} ⊆ s ∧ inf' {a} (_ : Finset.Nonempty {a}) id = a

Next tactic:
simpa
/-- Every set in a join-semilattice generates a set closed under join. -/
@[simps! isClosed]
def infClosure : ClosureOperator (Set α) := ClosureOperator.ofPred
  (λ s ↦ {a | ∃ (t : Finset α) (ht : t.Nonempty), ↑t ⊆ s ∧ t.inf' ht id = a})
  InfClosed
  (λ s a ha ↦ ⟨{a}, singleton_nonempty _, by simpa⟩)
  (by
    

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s t : Set α
a b : α
⊢ ∀ (x : Set α), InfClosed ((fun s => {a | ∃ t, ∃ (ht : Finset.Nonempty t), ↑t ⊆ s ∧ inf' t ht id = a}) x)

Next tactic:
classical
    rintro s _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
    refine' ⟨_, ht.mono $ subset_union_left _ _, _, inf'_union ht hu _⟩
    rw [coe_union]
    exact Set.union_subset hts hus
/-- Every set in a join-semilattice generates a set closed under join. -/
@[simps! isClosed]
def infClosure : ClosureOperator (Set α) := ClosureOperator.ofPred
  (λ s ↦ {a | ∃ (t : Finset α) (ht : t.Nonempty), ↑t ⊆ s ∧ t.inf' ht id = a})
  InfClosed
  (λ s a ha ↦ ⟨{a}, singleton_nonempty _, by simpa⟩)
  (by
    classical
    

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s t : Set α
a b : α
⊢ ∀ (x : Set α), InfClosed ((fun s => {a | ∃ t, ∃ (ht : Finset.Nonempty t), ↑t ⊆ s ∧ inf' t ht id = a}) x)

Next tactic:
rintro s _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
/-- Every set in a join-semilattice generates a set closed under join. -/
@[simps! isClosed]
def infClosure : ClosureOperator (Set α) := ClosureOperator.ofPred
  (λ s ↦ {a | ∃ (t : Finset α) (ht : t.Nonempty), ↑t ⊆ s ∧ t.inf' ht id = a})
  InfClosed
  (λ s a ha ↦ ⟨{a}, singleton_nonempty _, by simpa⟩)
  (by
    classical
    rintro s _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
    

Proof state:
case intro.intro.intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s✝ t✝ : Set α
a b : α
s : Set α
t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ s
u : Finset α
hu : Finset.Nonempty u
hus : ↑u ⊆ s
⊢ inf' t ht id ⊓ inf' u hu id ∈ (fun s => {a | ∃ t, ∃ (ht : Finset.Nonempty t), ↑t ⊆ s ∧ inf' t ht id = a}) s

Next tactic:
refine' ⟨_, ht.mono $ subset_union_left _ _, _, inf'_union ht hu _⟩
/-- Every set in a join-semilattice generates a set closed under join. -/
@[simps! isClosed]
def infClosure : ClosureOperator (Set α) := ClosureOperator.ofPred
  (λ s ↦ {a | ∃ (t : Finset α) (ht : t.Nonempty), ↑t ⊆ s ∧ t.inf' ht id = a})
  InfClosed
  (λ s a ha ↦ ⟨{a}, singleton_nonempty _, by simpa⟩)
  (by
    classical
    rintro s _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
    refine' ⟨_, ht.mono $ subset_union_left _ _, _, inf'_union ht hu _⟩
    

Proof state:
case intro.intro.intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s✝ t✝ : Set α
a b : α
s : Set α
t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ s
u : Finset α
hu : Finset.Nonempty u
hus : ↑u ⊆ s
⊢ ↑(t ∪ u) ⊆ s

Next tactic:
rw [coe_union]
/-- Every set in a join-semilattice generates a set closed under join. -/
@[simps! isClosed]
def infClosure : ClosureOperator (Set α) := ClosureOperator.ofPred
  (λ s ↦ {a | ∃ (t : Finset α) (ht : t.Nonempty), ↑t ⊆ s ∧ t.inf' ht id = a})
  InfClosed
  (λ s a ha ↦ ⟨{a}, singleton_nonempty _, by simpa⟩)
  (by
    classical
    rintro s _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
    refine' ⟨_, ht.mono $ subset_union_left _ _, _, inf'_union ht hu _⟩
    rw [coe_union]
    

Proof state:
case intro.intro.intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s✝ t✝ : Set α
a b : α
s : Set α
t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ s
u : Finset α
hu : Finset.Nonempty u
hus : ↑u ⊆ s
⊢ ↑t ∪ ↑u ⊆ s

Next tactic:
exact Set.union_subset hts hus
/-- Every set in a join-semilattice generates a set closed under join. -/
@[simps! isClosed]
def infClosure : ClosureOperator (Set α) := ClosureOperator.ofPred
  (λ s ↦ {a | ∃ (t : Finset α) (ht : t.Nonempty), ↑t ⊆ s ∧ t.inf' ht id = a})
  InfClosed
  (λ s a ha ↦ ⟨{a}, singleton_nonempty _, by simpa⟩)
  (by
    classical
    rintro s _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
    refine' ⟨_, ht.mono $ subset_union_left _ _, _, inf'_union ht hu _⟩
    rw [coe_union]
    exact Set.union_subset hts hus)
  (by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s t : Set α
a b : α
⊢ ∀ ⦃x y : Set α⦄,
    x ≤ y → InfClosed y → (fun s => {a | ∃ t, ∃ (ht : Finset.Nonempty t), ↑t ⊆ s ∧ inf' t ht id = a}) x ≤ y

Next tactic:
rintro s₁ s₂ hs h₂ _ ⟨t, ht, hts, rfl⟩
/-- Every set in a join-semilattice generates a set closed under join. -/
@[simps! isClosed]
def infClosure : ClosureOperator (Set α) := ClosureOperator.ofPred
  (λ s ↦ {a | ∃ (t : Finset α) (ht : t.Nonempty), ↑t ⊆ s ∧ t.inf' ht id = a})
  InfClosed
  (λ s a ha ↦ ⟨{a}, singleton_nonempty _, by simpa⟩)
  (by
    classical
    rintro s _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
    refine' ⟨_, ht.mono $ subset_union_left _ _, _, inf'_union ht hu _⟩
    rw [coe_union]
    exact Set.union_subset hts hus)
  (by rintro s₁ s₂ hs h₂ _ ⟨t, ht, hts, rfl⟩; 

Proof state:
case intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s t✝ : Set α
a b : α
s₁ s₂ : Set α
hs : s₁ ≤ s₂
h₂ : InfClosed s₂
t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ s₁
⊢ inf' t ht id ∈ s₂

Next tactic:
exact h₂.finsetInf'_mem ht λ i hi ↦ hs $ hts hi
@[simp] lemma infClosure_empty : infClosure (∅ : Set α) = ∅ := by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s t : Set α
a b : α
⊢ infClosure ∅ = ∅

Next tactic:
simp
@[simp] lemma infClosure_singleton : infClosure {a} = {a} := by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s t : Set α
a b : α
⊢ infClosure {a} = {a}

Next tactic:
simp
@[simp] lemma infClosure_univ : infClosure (Set.univ : Set α) = Set.univ := by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s t : Set α
a b : α
⊢ infClosure Set.univ = Set.univ

Next tactic:
simp
@[simp] lemma lowerBounds_infClosure (s : Set α) : lowerBounds (infClosure s) = lowerBounds s :=
(lowerBounds_mono_set subset_infClosure).antisymm $ by
  

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s✝ t : Set α
a b : α
s : Set α
⊢ lowerBounds s ⊆ lowerBounds (infClosure s)

Next tactic:
rintro a ha _ ⟨t, ht, hts, rfl⟩
@[simp] lemma lowerBounds_infClosure (s : Set α) : lowerBounds (infClosure s) = lowerBounds s :=
(lowerBounds_mono_set subset_infClosure).antisymm $ by
  rintro a ha _ ⟨t, ht, hts, rfl⟩
  

Proof state:
case intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s✝ t✝ : Set α
a✝ b : α
s : Set α
a : α
ha : a ∈ lowerBounds s
t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ s
⊢ a ≤ inf' t ht id

Next tactic:
exact le_inf' _ _ λ b hb ↦ ha $ hts hb
@[simp] lemma isGLB_infClosure : IsGLB (infClosure s) a ↔ IsGLB s a := by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s t : Set α
a b : α
⊢ IsGLB (infClosure s) a ↔ IsGLB s a

Next tactic:
simp [IsGLB]
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.infClosure (hs : s.Finite) : (infClosure s).Finite := by
  

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
s t : Set α
a b : α
hs : Set.Finite s
⊢ Set.Finite (infClosure s)

Next tactic:
lift s to Finset α using hs
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.infClosure (hs : s.Finite) : (infClosure s).Finite := by
  lift s to Finset α using hs
  

Proof state:
case intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
t : Set α
a b : α
s : Finset α
⊢ Set.Finite (infClosure ↑s)

Next tactic:
classical
  refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.inf' (mem_filter.1 t.2).2 id).finite_toSet.subset _
  rintro _ ⟨t, ht, hts, rfl⟩
  simp only [id_eq, coe_image, mem_image, mem_coe, mem_attach, true_and, Subtype.exists,
    Finset.mem_powerset, Finset.not_nonempty_iff_eq_empty, mem_filter]
  exact ⟨t, ⟨hts, ht⟩, rfl⟩
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.infClosure (hs : s.Finite) : (infClosure s).Finite := by
  lift s to Finset α using hs
  classical
  

Proof state:
case intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
t : Set α
a b : α
s : Finset α
⊢ Set.Finite (infClosure ↑s)

Next tactic:
refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.inf' (mem_filter.1 t.2).2 id).finite_toSet.subset _
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.infClosure (hs : s.Finite) : (infClosure s).Finite := by
  lift s to Finset α using hs
  classical
  refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.inf' (mem_filter.1 t.2).2 id).finite_toSet.subset _
  

Proof state:
case intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
t : Set α
a b : α
s : Finset α
⊢ infClosure ↑s ⊆
    ↑(Finset.image (fun t => inf' ↑t (_ : Finset.Nonempty ↑t) id) (attach (filter Finset.Nonempty (Finset.powerset s))))

Next tactic:
rintro _ ⟨t, ht, hts, rfl⟩
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.infClosure (hs : s.Finite) : (infClosure s).Finite := by
  lift s to Finset α using hs
  classical
  refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.inf' (mem_filter.1 t.2).2 id).finite_toSet.subset _
  rintro _ ⟨t, ht, hts, rfl⟩
  

Proof state:
case intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
t✝ : Set α
a b : α
s t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ ↑s
⊢ inf' t ht id ∈
    ↑(Finset.image (fun t => inf' ↑t (_ : Finset.Nonempty ↑t) id) (attach (filter Finset.Nonempty (Finset.powerset s))))

Next tactic:
simp only [id_eq, coe_image, mem_image, mem_coe, mem_attach, true_and, Subtype.exists,
    Finset.mem_powerset, Finset.not_nonempty_iff_eq_empty, mem_filter]
/-- The semilatice generated by a finite set is finite. -/
protected lemma Set.Finite.infClosure (hs : s.Finite) : (infClosure s).Finite := by
  lift s to Finset α using hs
  classical
  refine' ((s.powerset.filter Finset.Nonempty).attach.image
    fun t ↦ t.1.inf' (mem_filter.1 t.2).2 id).finite_toSet.subset _
  rintro _ ⟨t, ht, hts, rfl⟩
  simp only [id_eq, coe_image, mem_image, mem_coe, mem_attach, true_and, Subtype.exists,
    Finset.mem_powerset, Finset.not_nonempty_iff_eq_empty, mem_filter]
  

Proof state:
case intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : SemilatticeInf α
inst✝ : SemilatticeInf β
t✝ : Set α
a b : α
s t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ ↑s
⊢ ∃ a,
    ∃ (h : a ⊆ s ∧ Finset.Nonempty a),
      (inf' a (_ : Finset.Nonempty ↑{ val := a, property := (_ : a ∈ filter Finset.Nonempty (Finset.powerset s)) })
          fun x => x) =
        inf' t (_ : Finset.Nonempty t) fun x => x

Next tactic:
exact ⟨t, ⟨hts, ht⟩, rfl⟩
@[simp] lemma latticeClosure_empty : latticeClosure (∅ : Set α) = ∅ := by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝ : Lattice α
s t : Set α
⊢ latticeClosure ∅ = ∅

Next tactic:
simp
@[simp] lemma latticeClosure_singleton (a : α) : latticeClosure {a} = {a} := by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝ : Lattice α
s t : Set α
a : α
⊢ latticeClosure {a} = {a}

Next tactic:
simp
@[simp] lemma latticeClosure_univ : latticeClosure (Set.univ : Set α) = Set.univ := by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝ : Lattice α
s t : Set α
⊢ latticeClosure Set.univ = Set.univ

Next tactic:
simp
protected lemma SupClosed.infClosure (hs : SupClosed s) : SupClosed (infClosure s) := by
  

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : DistribLattice α
inst✝ : DistribLattice β
s : Set α
hs : SupClosed s
⊢ SupClosed (infClosure s)

Next tactic:
rintro _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
protected lemma SupClosed.infClosure (hs : SupClosed s) : SupClosed (infClosure s) := by
  rintro _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
  

Proof state:
case intro.intro.intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : DistribLattice α
inst✝ : DistribLattice β
s : Set α
hs : SupClosed s
t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ s
u : Finset α
hu : Finset.Nonempty u
hus : ↑u ⊆ s
⊢ inf' t ht id ⊔ inf' u hu id ∈ infClosure s

Next tactic:
rw [inf'_sup_inf']
protected lemma SupClosed.infClosure (hs : SupClosed s) : SupClosed (infClosure s) := by
  rintro _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
  rw [inf'_sup_inf']
  

Proof state:
case intro.intro.intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : DistribLattice α
inst✝ : DistribLattice β
s : Set α
hs : SupClosed s
t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ s
u : Finset α
hu : Finset.Nonempty u
hus : ↑u ⊆ s
⊢ (inf' (t ×ˢ u) (_ : Finset.Nonempty (t ×ˢ u)) fun i => id i.1 ⊔ id i.2) ∈ infClosure s

Next tactic:
exact finsetInf'_mem_infClosure _
    fun i hi ↦ hs (hts (mem_product.1 hi).1) (hus (mem_product.1 hi).2)
protected lemma InfClosed.supClosure (hs : InfClosed s) : InfClosed (supClosure s) := by
  

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : DistribLattice α
inst✝ : DistribLattice β
s : Set α
hs : InfClosed s
⊢ InfClosed (supClosure s)

Next tactic:
rintro _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
protected lemma InfClosed.supClosure (hs : InfClosed s) : InfClosed (supClosure s) := by
  rintro _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
  

Proof state:
case intro.intro.intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : DistribLattice α
inst✝ : DistribLattice β
s : Set α
hs : InfClosed s
t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ s
u : Finset α
hu : Finset.Nonempty u
hus : ↑u ⊆ s
⊢ sup' t ht id ⊓ sup' u hu id ∈ supClosure s

Next tactic:
rw [sup'_inf_sup']
protected lemma InfClosed.supClosure (hs : InfClosed s) : InfClosed (supClosure s) := by
  rintro _ ⟨t, ht, hts, rfl⟩ _ ⟨u, hu, hus, rfl⟩
  rw [sup'_inf_sup']
  

Proof state:
case intro.intro.intro.intro.intro.intro
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : DistribLattice α
inst✝ : DistribLattice β
s : Set α
hs : InfClosed s
t : Finset α
ht : Finset.Nonempty t
hts : ↑t ⊆ s
u : Finset α
hu : Finset.Nonempty u
hus : ↑u ⊆ s
⊢ (sup' (t ×ˢ u) (_ : Finset.Nonempty (t ×ˢ u)) fun i => id i.1 ⊓ id i.2) ∈ supClosure s

Next tactic:
exact finsetSup'_mem_supClosure _
    fun i hi ↦ hs (hts (mem_product.1 hi).1) (hus (mem_product.1 hi).2)
lemma Set.Finite.latticeClosure (hs : s.Finite) : (latticeClosure s).Finite := by
  

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : DistribLattice α
inst✝ : DistribLattice β
s : Set α
hs : Set.Finite s
⊢ Set.Finite (_root_.latticeClosure s)

Next tactic:
rw [← supClosure_infClosure]
lemma Set.Finite.latticeClosure (hs : s.Finite) : (latticeClosure s).Finite := by
  rw [← supClosure_infClosure]; 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝¹ : DistribLattice α
inst✝ : DistribLattice β
s : Set α
hs : Set.Finite s
⊢ Set.Finite (supClosure (infClosure s))

Next tactic:
exact hs.infClosure.supClosure
/-- A join-semilattice where every sup-closed set has a least upper bound is automatically complete.
-/
def SemilatticeSup.toCompleteSemilatticeSup [SemilatticeSup α] (sSup : Set α → α)
    (h : ∀ s, SupClosed s → IsLUB s (sSup s)) : CompleteSemilatticeSup α where
  sSup := fun s => sSup (supClosure s)
  le_sSup s a ha := (h _ supClosed_supClosure).1 $ subset_supClosure ha
  sSup_le s a ha := (isLUB_le_iff $ h _ supClosed_supClosure).2 $ by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝ : SemilatticeSup α
sSup : Set α → α
h : ∀ (s : Set α), SupClosed s → IsLUB s (sSup s)
s : Set α
a : α
ha : ∀ b ∈ s, b ≤ a
⊢ a ∈ upperBounds (supClosure s)

Next tactic:
rwa [upperBounds_supClosure]
/-- A meet-semilattice where every inf-closed set has a greatest lower bound is automatically
complete. -/
def SemilatticeInf.toCompleteSemilatticeInf [SemilatticeInf α] (sInf : Set α → α)
    (h : ∀ s, InfClosed s → IsGLB s (sInf s)) : CompleteSemilatticeInf α where
  sInf := fun s => sInf (infClosure s)
  sInf_le s a ha := (h _ infClosed_infClosure).1 $ subset_infClosure ha
  le_sInf s a ha := (le_isGLB_iff $ h _ infClosed_infClosure).2 $ by 

Proof state:
F : Type u_1
α : Type u_2
β : Type u_3
inst✝ : SemilatticeInf α
sInf : Set α → α
h : ∀ (s : Set α), InfClosed s → IsGLB s (sInf s)
s : Set α
a : α
ha : ∀ b ∈ s, a ≤ b
⊢ a ∈ lowerBounds (infClosure s)

Next tactic:
rwa [lowerBounds_infClosure]
/-- Pullback a `SMulWithZero` structure along an injective zero-preserving homomorphism.
See note [reducible non-instances]. -/
@[reducible]
protected def Function.Injective.smulWithZero (f : ZeroHom M' M) (hf : Function.Injective f)
    (smul : ∀ (a : R) (b), f (a • b) = a • f b) :
    SMulWithZero R M' where
  smul := (· • ·)
  zero_smul a := hf <| by simp [smul]
  smul_zero a := hf <| by 

Proof state:
R : Type u_1
R' : Type u_2
M : Type u_3
M' : Type u_4
inst✝⁵ : Zero R
inst✝⁴ : Zero M
inst✝³ : SMulWithZero R M
a✝ : R
b : M
inst✝² : Zero R'
inst✝¹ : Zero M'
inst✝ : SMul R M'
f : ZeroHom M' M
hf : Injective ⇑f
smul : ∀ (a : R) (b : M'), f (a • b) = a • f b
a : R
⊢ f (a • 0) = f 0

Next tactic:
simp [smul]
/-- Pullback a `SMulWithZero` structure along an injective zero-preserving homomorphism.
See note [reducible non-instances]. -/
@[reducible]
protected def Function.Injective.smulWithZero (f : ZeroHom M' M) (hf : Function.Injective f)
    (smul : ∀ (a : R) (b), f (a • b) = a • f b) :
    SMulWithZero R M' where
  smul := (· • ·)
  zero_smul a := hf <| by 

Proof state:
R : Type u_1
R' : Type u_2
M : Type u_3
M' : Type u_4
inst✝⁵ : Zero R
inst✝⁴ : Zero M
inst✝³ : SMulWithZero R M
a✝ : R
b : M
inst✝² : Zero R'
inst✝¹ : Zero M'
inst✝ : SMul R M'
f : ZeroHom M' M
hf : Injective ⇑f
smul : ∀ (a : R) (b : M'), f (a • b) = a • f b
a : M'
⊢ f (0 • a) = f 0

Next tactic:
simp [smul]
/-- Pushforward a `SMulWithZero` structure along a surjective zero-preserving homomorphism.
See note [reducible non-instances]. -/
@[reducible]
protected def Function.Surjective.smulWithZero (f : ZeroHom M M') (hf : Function.Surjective f)
    (smul : ∀ (a : R) (b), f (a • b) = a • f b) :
    SMulWithZero R M' where
  smul := (· • ·)
  zero_smul m := by
    rcases hf m with ⟨x, rfl⟩
    simp [← smul]
  smul_zero c := by 

Proof state:
R : Type u_1
R' : Type u_2
M : Type u_3
M' : Type u_4
inst✝⁵ : Zero R
inst✝⁴ : Zero M
inst✝³ : SMulWithZero R M
a : R
b : M
inst✝² : Zero R'
inst✝¹ : Zero M'
inst✝ : SMul R M'
f : ZeroHom M M'
hf : Surjective ⇑f
smul : ∀ (a : R) (b : M), f (a • b) = a • f b
c : R
⊢ c • 0 = 0

Next tactic:
rw [← f.map_zero, ← smul, smul_zero]
/-- Pushforward a `SMulWithZero` structure along a surjective zero-preserving homomorphism.
See note [reducible non-instances]. -/
@[reducible]
protected def Function.Surjective.smulWithZero (f : ZeroHom M M') (hf : Function.Surjective f)
    (smul : ∀ (a : R) (b), f (a • b) = a • f b) :
    SMulWithZero R M' where
  smul := (· • ·)
  zero_smul m := by
    

Proof state:
R : Type u_1
R' : Type u_2
M : Type u_3
M' : Type u_4
inst✝⁵ : Zero R
inst✝⁴ : Zero M
inst✝³ : SMulWithZero R M
a : R
b : M
inst✝² : Zero R'
inst✝¹ : Zero M'
inst✝ : SMul R M'
f : ZeroHom M M'
hf : Surjective ⇑f
smul : ∀ (a : R) (b : M), f (a • b) = a • f b
m : M'
⊢ 0 • m = 0

Next tactic:
rcases hf m with ⟨x, rfl⟩