l3lab/ntp-mathlib huggingface dataset:
theorem einfsep_insert : einfsep (insert x s) =
    (⨅ (y ∈ s) (_ : x ≠ y), edist x y) ⊓ s.einfsep := by
  refine' le_antisymm (le_min einfsep_insert_le (einfsep_anti (subset_insert _ _))) _
  simp_rw [le_einfsep_iff, inf_le_iff, mem_insert_iff]
  rintro y (rfl | hy) z (rfl | hz) hyz
  · exact False.elim (hyz rfl)
  · exact Or.inl (iInf_le_of_le _ (iInf₂_le hz hyz))
  · rw [edist_comm]
    

Proof state:
case inr.inl
α : Type u_1
β : Type u_2
inst✝ : PseudoEMetricSpace α
y✝ z✝ : α
s t : Set α
y : α
hy : y ∈ s
z : α
hyz : y ≠ z
⊢ ⨅ y ∈ s, ⨅ (_ : z ≠ y), edist z y ≤ edist z y ∨ einfsep s ≤ edist z y

Next tactic:
exact Or.inl (iInf_le_of_le _ (iInf₂_le hy hyz.symm))
theorem einfsep_insert : einfsep (insert x s) =
    (⨅ (y ∈ s) (_ : x ≠ y), edist x y) ⊓ s.einfsep := by
  refine' le_antisymm (le_min einfsep_insert_le (einfsep_anti (subset_insert _ _))) _
  simp_rw [le_einfsep_iff, inf_le_iff, mem_insert_iff]
  rintro y (rfl | hy) z (rfl | hz) hyz
  · exact False.elim (hyz rfl)
  · exact Or.inl (iInf_le_of_le _ (iInf₂_le hz hyz))
  · rw [edist_comm]
    exact Or.inl (iInf_le_of_le _ (iInf₂_le hy hyz.symm))
  · 

Proof state:
case inr.inr
α : Type u_1
β : Type u_2
inst✝ : PseudoEMetricSpace α
x y✝ z✝ : α
s t : Set α
y : α
hy : y ∈ s
z : α
hz : z ∈ s
hyz : y ≠ z
⊢ ⨅ y ∈ s, ⨅ (_ : x ≠ y), edist x y ≤ edist y z ∨ einfsep s ≤ edist y z

Next tactic:
exact Or.inr (einfsep_le_edist_of_mem hy hz hyz)
theorem einfsep_triple (hxy : x ≠ y) (hyz : y ≠ z) (hxz : x ≠ z) :
    einfsep ({x, y, z} : Set α) = edist x y ⊓ edist x z ⊓ edist y z := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoEMetricSpace α
x y z : α
s t : Set α
hxy : x ≠ y
hyz : y ≠ z
hxz : x ≠ z
⊢ einfsep {x, y, z} = edist x y ⊓ edist x z ⊓ edist y z

Next tactic:
simp_rw [einfsep_insert, iInf_insert, iInf_singleton, einfsep_singleton, inf_top_eq,
    ciInf_pos hxy, ciInf_pos hyz, ciInf_pos hxz]
theorem le_einfsep_pi_of_le {π : β → Type*} [Fintype β] [∀ b, PseudoEMetricSpace (π b)]
    {s : ∀ b : β, Set (π b)} {c : ℝ≥0∞} (h : ∀ b, c ≤ einfsep (s b)) :
    c ≤ einfsep (Set.pi univ s) := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝² : PseudoEMetricSpace α
x y z : α
s✝ t : Set α
π : β → Type u_3
inst✝¹ : Fintype β
inst✝ : (b : β) → PseudoEMetricSpace (π b)
s : (b : β) → Set (π b)
c : ℝ≥0∞
h : ∀ (b : β), c ≤ einfsep (s b)
⊢ c ≤ einfsep (pi univ s)

Next tactic:
refine' le_einfsep fun x hx y hy hxy => _
theorem le_einfsep_pi_of_le {π : β → Type*} [Fintype β] [∀ b, PseudoEMetricSpace (π b)]
    {s : ∀ b : β, Set (π b)} {c : ℝ≥0∞} (h : ∀ b, c ≤ einfsep (s b)) :
    c ≤ einfsep (Set.pi univ s) := by
  refine' le_einfsep fun x hx y hy hxy => _
  

Proof state:
α : Type u_1
β : Type u_2
inst✝² : PseudoEMetricSpace α
x✝ y✝ z : α
s✝ t : Set α
π : β → Type u_3
inst✝¹ : Fintype β
inst✝ : (b : β) → PseudoEMetricSpace (π b)
s : (b : β) → Set (π b)
c : ℝ≥0∞
h : ∀ (b : β), c ≤ einfsep (s b)
x : (i : β) → π i
hx : x ∈ pi univ s
y : (i : β) → π i
hy : y ∈ pi univ s
hxy : x ≠ y
⊢ c ≤ edist x y

Next tactic:
rw [mem_univ_pi] at hx hy
theorem le_einfsep_pi_of_le {π : β → Type*} [Fintype β] [∀ b, PseudoEMetricSpace (π b)]
    {s : ∀ b : β, Set (π b)} {c : ℝ≥0∞} (h : ∀ b, c ≤ einfsep (s b)) :
    c ≤ einfsep (Set.pi univ s) := by
  refine' le_einfsep fun x hx y hy hxy => _
  rw [mem_univ_pi] at hx hy
  

Proof state:
α : Type u_1
β : Type u_2
inst✝² : PseudoEMetricSpace α
x✝ y✝ z : α
s✝ t : Set α
π : β → Type u_3
inst✝¹ : Fintype β
inst✝ : (b : β) → PseudoEMetricSpace (π b)
s : (b : β) → Set (π b)
c : ℝ≥0∞
h : ∀ (b : β), c ≤ einfsep (s b)
x : (i : β) → π i
hx : ∀ (i : β), x i ∈ s i
y : (i : β) → π i
hy : ∀ (i : β), y i ∈ s i
hxy : x ≠ y
⊢ c ≤ edist x y

Next tactic:
rcases Function.ne_iff.mp hxy with ⟨i, hi⟩
theorem le_einfsep_pi_of_le {π : β → Type*} [Fintype β] [∀ b, PseudoEMetricSpace (π b)]
    {s : ∀ b : β, Set (π b)} {c : ℝ≥0∞} (h : ∀ b, c ≤ einfsep (s b)) :
    c ≤ einfsep (Set.pi univ s) := by
  refine' le_einfsep fun x hx y hy hxy => _
  rw [mem_univ_pi] at hx hy
  rcases Function.ne_iff.mp hxy with ⟨i, hi⟩
  

Proof state:
case intro
α : Type u_1
β : Type u_2
inst✝² : PseudoEMetricSpace α
x✝ y✝ z : α
s✝ t : Set α
π : β → Type u_3
inst✝¹ : Fintype β
inst✝ : (b : β) → PseudoEMetricSpace (π b)
s : (b : β) → Set (π b)
c : ℝ≥0∞
h : ∀ (b : β), c ≤ einfsep (s b)
x : (i : β) → π i
hx : ∀ (i : β), x i ∈ s i
y : (i : β) → π i
hy : ∀ (i : β), y i ∈ s i
hxy : x ≠ y
i : β
hi : x i ≠ y i
⊢ c ≤ edist x y

Next tactic:
exact le_trans (le_einfsep_iff.1 (h i) _ (hx _) _ (hy _) hi) (edist_le_pi_edist _ _ i)
theorem subsingleton_of_einfsep_eq_top (hs : s.einfsep = ∞) : s.Subsingleton := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
s : Set α
hs : einfsep s = ⊤
⊢ Set.Subsingleton s

Next tactic:
rw [einfsep_top] at hs
theorem subsingleton_of_einfsep_eq_top (hs : s.einfsep = ∞) : s.Subsingleton := by
  rw [einfsep_top] at hs
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
s : Set α
hs : ∀ x ∈ s, ∀ y ∈ s, x ≠ y → edist x y = ⊤
⊢ Set.Subsingleton s

Next tactic:
exact fun _ hx _ hy => of_not_not fun hxy => edist_ne_top _ _ (hs _ hx _ hy hxy)
theorem Nontrivial.einfsep_ne_top (hs : s.Nontrivial) : s.einfsep ≠ ∞ := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
s : Set α
hs : Set.Nontrivial s
⊢ einfsep s ≠ ⊤

Next tactic:
contrapose! hs
theorem Nontrivial.einfsep_ne_top (hs : s.Nontrivial) : s.einfsep ≠ ∞ := by
  contrapose! hs
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
s : Set α
hs : einfsep s = ⊤
⊢ ¬Set.Nontrivial s

Next tactic:
rw [not_nontrivial_iff]
theorem Nontrivial.einfsep_ne_top (hs : s.Nontrivial) : s.einfsep ≠ ∞ := by
  contrapose! hs
  rw [not_nontrivial_iff]
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
s : Set α
hs : einfsep s = ⊤
⊢ Set.Subsingleton s

Next tactic:
exact subsingleton_of_einfsep_eq_top hs
theorem Nontrivial.einfsep_lt_top (hs : s.Nontrivial) : s.einfsep < ∞ := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
s : Set α
hs : Set.Nontrivial s
⊢ einfsep s < ⊤

Next tactic:
rw [lt_top_iff_ne_top]
theorem Nontrivial.einfsep_lt_top (hs : s.Nontrivial) : s.einfsep < ∞ := by
  rw [lt_top_iff_ne_top]
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
s : Set α
hs : Set.Nontrivial s
⊢ einfsep s ≠ ⊤

Next tactic:
exact hs.einfsep_ne_top
theorem einfsep_pos_of_finite [Finite s] : 0 < s.einfsep := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : EMetricSpace α
x y z : α
s t : Set α
C : ℝ≥0∞
sC : Set ℝ≥0∞
inst✝ : Finite ↑s
⊢ 0 < einfsep s

Next tactic:
cases nonempty_fintype s
theorem einfsep_pos_of_finite [Finite s] : 0 < s.einfsep := by
  cases nonempty_fintype s
  

Proof state:
case intro
α : Type u_1
β : Type u_2
inst✝¹ : EMetricSpace α
x y z : α
s t : Set α
C : ℝ≥0∞
sC : Set ℝ≥0∞
inst✝ : Finite ↑s
val✝ : Fintype ↑s
⊢ 0 < einfsep s

Next tactic:
by_cases hs : s.Nontrivial
theorem einfsep_pos_of_finite [Finite s] : 0 < s.einfsep := by
  cases nonempty_fintype s
  by_cases hs : s.Nontrivial
  · 

Proof state:
case pos
α : Type u_1
β : Type u_2
inst✝¹ : EMetricSpace α
x y z : α
s t : Set α
C : ℝ≥0∞
sC : Set ℝ≥0∞
inst✝ : Finite ↑s
val✝ : Fintype ↑s
hs : Set.Nontrivial s
⊢ 0 < einfsep s

Next tactic:
rcases hs.einfsep_exists_of_finite with ⟨x, _hx, y, _hy, hxy, hxy'⟩
theorem einfsep_pos_of_finite [Finite s] : 0 < s.einfsep := by
  cases nonempty_fintype s
  by_cases hs : s.Nontrivial
  · rcases hs.einfsep_exists_of_finite with ⟨x, _hx, y, _hy, hxy, hxy'⟩
    

Proof state:
case pos.intro.intro.intro.intro.intro
α : Type u_1
β : Type u_2
inst✝¹ : EMetricSpace α
x✝ y✝ z : α
s t : Set α
C : ℝ≥0∞
sC : Set ℝ≥0∞
inst✝ : Finite ↑s
val✝ : Fintype ↑s
hs : Set.Nontrivial s
x : α
_hx : x ∈ s
y : α
_hy : y ∈ s
hxy : x ≠ y
hxy' : einfsep s = edist x y
⊢ 0 < einfsep s

Next tactic:
exact hxy'.symm ▸ edist_pos.2 hxy
theorem einfsep_pos_of_finite [Finite s] : 0 < s.einfsep := by
  cases nonempty_fintype s
  by_cases hs : s.Nontrivial
  · rcases hs.einfsep_exists_of_finite with ⟨x, _hx, y, _hy, hxy, hxy'⟩
    exact hxy'.symm ▸ edist_pos.2 hxy
  · 

Proof state:
case neg
α : Type u_1
β : Type u_2
inst✝¹ : EMetricSpace α
x y z : α
s t : Set α
C : ℝ≥0∞
sC : Set ℝ≥0∞
inst✝ : Finite ↑s
val✝ : Fintype ↑s
hs : ¬Set.Nontrivial s
⊢ 0 < einfsep s

Next tactic:
rw [not_nontrivial_iff] at hs
theorem einfsep_pos_of_finite [Finite s] : 0 < s.einfsep := by
  cases nonempty_fintype s
  by_cases hs : s.Nontrivial
  · rcases hs.einfsep_exists_of_finite with ⟨x, _hx, y, _hy, hxy, hxy'⟩
    exact hxy'.symm ▸ edist_pos.2 hxy
  · rw [not_nontrivial_iff] at hs
    

Proof state:
case neg
α : Type u_1
β : Type u_2
inst✝¹ : EMetricSpace α
x y z : α
s t : Set α
C : ℝ≥0∞
sC : Set ℝ≥0∞
inst✝ : Finite ↑s
val✝ : Fintype ↑s
hs : Set.Subsingleton s
⊢ 0 < einfsep s

Next tactic:
exact hs.einfsep.symm ▸ WithTop.zero_lt_top
theorem relatively_discrete_of_finite [Finite s] :
    ∃ C > 0, ∀ x ∈ s, ∀ y ∈ s, x ≠ y → C ≤ edist x y := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : EMetricSpace α
x y z : α
s t : Set α
C : ℝ≥0∞
sC : Set ℝ≥0∞
inst✝ : Finite ↑s
⊢ ∃ C > 0, ∀ x ∈ s, ∀ y ∈ s, x ≠ y → C ≤ edist x y

Next tactic:
rw [← einfsep_pos]
theorem relatively_discrete_of_finite [Finite s] :
    ∃ C > 0, ∀ x ∈ s, ∀ y ∈ s, x ≠ y → C ≤ edist x y := by
  rw [← einfsep_pos]
  

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : EMetricSpace α
x y z : α
s t : Set α
C : ℝ≥0∞
sC : Set ℝ≥0∞
inst✝ : Finite ↑s
⊢ 0 < einfsep s

Next tactic:
exact einfsep_pos_of_finite
theorem infsep_zero : s.infsep = 0 ↔ s.einfsep = 0 ∨ s.einfsep = ∞ := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : EDist α
x y : α
s : Set α
⊢ infsep s = 0 ↔ einfsep s = 0 ∨ einfsep s = ⊤

Next tactic:
rw [infsep, ENNReal.toReal_eq_zero_iff]
theorem infsep_pos : 0 < s.infsep ↔ 0 < s.einfsep ∧ s.einfsep < ∞ := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : EDist α
x y : α
s : Set α
⊢ 0 < infsep s ↔ 0 < einfsep s ∧ einfsep s < ⊤

Next tactic:
simp_rw [infsep, ENNReal.toReal_pos_iff]
theorem nontrivial_of_infsep_pos (hs : 0 < s.infsep) : s.Nontrivial := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : EDist α
x y : α
s : Set α
hs : 0 < infsep s
⊢ Set.Nontrivial s

Next tactic:
contrapose hs
theorem nontrivial_of_infsep_pos (hs : 0 < s.infsep) : s.Nontrivial := by
  contrapose hs
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : EDist α
x y : α
s : Set α
hs : ¬Set.Nontrivial s
⊢ ¬0 < infsep s

Next tactic:
rw [not_nontrivial_iff] at hs
theorem nontrivial_of_infsep_pos (hs : 0 < s.infsep) : s.Nontrivial := by
  contrapose hs
  rw [not_nontrivial_iff] at hs
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : EDist α
x y : α
s : Set α
hs : Set.Subsingleton s
⊢ ¬0 < infsep s

Next tactic:
exact hs.infsep_zero ▸ lt_irrefl _
theorem infsep_pair_le_toReal_inf (hxy : x ≠ y) :
    ({x, y} : Set α).infsep ≤ (edist x y ⊓ edist y x).toReal := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : EDist α
x y : α
s : Set α
hxy : x ≠ y
⊢ infsep {x, y} ≤ ENNReal.toReal (edist x y ⊓ edist y x)

Next tactic:
simp_rw [infsep, einfsep_pair_eq_inf hxy]
theorem infsep_pair_le_toReal_inf (hxy : x ≠ y) :
    ({x, y} : Set α).infsep ≤ (edist x y ⊓ edist y x).toReal := by
  simp_rw [infsep, einfsep_pair_eq_inf hxy]
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : EDist α
x y : α
s : Set α
hxy : x ≠ y
⊢ ENNReal.toReal (edist x y ⊓ edist y x) ≤ ENNReal.toReal (edist x y ⊓ edist y x)

Next tactic:
simp
theorem infsep_pair_eq_toReal : ({x, y} : Set α).infsep = (edist x y).toReal := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoEMetricSpace α
x y : α
s : Set α
⊢ infsep {x, y} = ENNReal.toReal (edist x y)

Next tactic:
by_cases hxy : x = y
theorem infsep_pair_eq_toReal : ({x, y} : Set α).infsep = (edist x y).toReal := by
  by_cases hxy : x = y
  · 

Proof state:
case pos
α : Type u_1
β : Type u_2
inst✝ : PseudoEMetricSpace α
x y : α
s : Set α
hxy : x = y
⊢ infsep {x, y} = ENNReal.toReal (edist x y)

Next tactic:
rw [hxy]
theorem infsep_pair_eq_toReal : ({x, y} : Set α).infsep = (edist x y).toReal := by
  by_cases hxy : x = y
  · rw [hxy]
    

Proof state:
case pos
α : Type u_1
β : Type u_2
inst✝ : PseudoEMetricSpace α
x y : α
s : Set α
hxy : x = y
⊢ infsep {y, y} = ENNReal.toReal (edist y y)

Next tactic:
simp only [infsep_singleton, pair_eq_singleton, edist_self, ENNReal.zero_toReal]
theorem infsep_pair_eq_toReal : ({x, y} : Set α).infsep = (edist x y).toReal := by
  by_cases hxy : x = y
  · rw [hxy]
    simp only [infsep_singleton, pair_eq_singleton, edist_self, ENNReal.zero_toReal]
  · 

Proof state:
case neg
α : Type u_1
β : Type u_2
inst✝ : PseudoEMetricSpace α
x y : α
s : Set α
hxy : ¬x = y
⊢ infsep {x, y} = ENNReal.toReal (edist x y)

Next tactic:
rw [infsep, einfsep_pair hxy]
theorem Nontrivial.le_infsep_iff {d} (hs : s.Nontrivial) :
    d ≤ s.infsep ↔ ∀ x ∈ s, ∀ y ∈ s, x ≠ y → d ≤ dist x y := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x y z : α
s t : Set α
d : ℝ
hs : Set.Nontrivial s
⊢ d ≤ infsep s ↔ ∀ x ∈ s, ∀ y ∈ s, x ≠ y → d ≤ dist x y

Next tactic:
simp_rw [infsep, ← ENNReal.ofReal_le_iff_le_toReal hs.einfsep_ne_top, le_einfsep_iff, edist_dist,
    ENNReal.ofReal_le_ofReal_iff dist_nonneg]
theorem Nontrivial.infsep_lt_iff {d} (hs : s.Nontrivial) :
    s.infsep < d ↔ ∃ x ∈ s, ∃ y ∈ s, x ≠ y ∧ dist x y < d := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x y z : α
s t : Set α
d : ℝ
hs : Set.Nontrivial s
⊢ infsep s < d ↔ ∃ x ∈ s, ∃ y ∈ s, x ≠ y ∧ dist x y < d

Next tactic:
rw [← not_iff_not]
theorem Nontrivial.infsep_lt_iff {d} (hs : s.Nontrivial) :
    s.infsep < d ↔ ∃ x ∈ s, ∃ y ∈ s, x ≠ y ∧ dist x y < d := by
  rw [← not_iff_not]
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x y z : α
s t : Set α
d : ℝ
hs : Set.Nontrivial s
⊢ ¬infsep s < d ↔ ¬∃ x ∈ s, ∃ y ∈ s, x ≠ y ∧ dist x y < d

Next tactic:
push_neg
theorem Nontrivial.infsep_lt_iff {d} (hs : s.Nontrivial) :
    s.infsep < d ↔ ∃ x ∈ s, ∃ y ∈ s, x ≠ y ∧ dist x y < d := by
  rw [← not_iff_not]
  push_neg
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x y z : α
s t : Set α
d : ℝ
hs : Set.Nontrivial s
⊢ d ≤ infsep s ↔ ∀ x ∈ s, ∀ y ∈ s, x ≠ y → d ≤ dist x y

Next tactic:
exact hs.le_infsep_iff
theorem le_edist_of_le_infsep {d x} (hx : x ∈ s) {y} (hy : y ∈ s) (hxy : x ≠ y)
    (hd : d ≤ s.infsep) : d ≤ dist x y := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x✝ y✝ z : α
s t : Set α
d : ℝ
x : α
hx : x ∈ s
y : α
hy : y ∈ s
hxy : x ≠ y
hd : d ≤ infsep s
⊢ d ≤ dist x y

Next tactic:
by_cases hs : s.Nontrivial
theorem le_edist_of_le_infsep {d x} (hx : x ∈ s) {y} (hy : y ∈ s) (hxy : x ≠ y)
    (hd : d ≤ s.infsep) : d ≤ dist x y := by
  by_cases hs : s.Nontrivial
  · 

Proof state:
case pos
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x✝ y✝ z : α
s t : Set α
d : ℝ
x : α
hx : x ∈ s
y : α
hy : y ∈ s
hxy : x ≠ y
hd : d ≤ infsep s
hs : Set.Nontrivial s
⊢ d ≤ dist x y

Next tactic:
exact hs.le_infsep_iff.1 hd x hx y hy hxy
theorem le_edist_of_le_infsep {d x} (hx : x ∈ s) {y} (hy : y ∈ s) (hxy : x ≠ y)
    (hd : d ≤ s.infsep) : d ≤ dist x y := by
  by_cases hs : s.Nontrivial
  · exact hs.le_infsep_iff.1 hd x hx y hy hxy
  · 

Proof state:
case neg
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x✝ y✝ z : α
s t : Set α
d : ℝ
x : α
hx : x ∈ s
y : α
hy : y ∈ s
hxy : x ≠ y
hd : d ≤ infsep s
hs : ¬Set.Nontrivial s
⊢ d ≤ dist x y

Next tactic:
rw [not_nontrivial_iff] at hs
theorem le_edist_of_le_infsep {d x} (hx : x ∈ s) {y} (hy : y ∈ s) (hxy : x ≠ y)
    (hd : d ≤ s.infsep) : d ≤ dist x y := by
  by_cases hs : s.Nontrivial
  · exact hs.le_infsep_iff.1 hd x hx y hy hxy
  · rw [not_nontrivial_iff] at hs
    

Proof state:
case neg
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x✝ y✝ z : α
s t : Set α
d : ℝ
x : α
hx : x ∈ s
y : α
hy : y ∈ s
hxy : x ≠ y
hd : d ≤ infsep s
hs : Set.Subsingleton s
⊢ d ≤ dist x y

Next tactic:
rw [hs.infsep_zero] at hd
theorem le_edist_of_le_infsep {d x} (hx : x ∈ s) {y} (hy : y ∈ s) (hxy : x ≠ y)
    (hd : d ≤ s.infsep) : d ≤ dist x y := by
  by_cases hs : s.Nontrivial
  · exact hs.le_infsep_iff.1 hd x hx y hy hxy
  · rw [not_nontrivial_iff] at hs
    rw [hs.infsep_zero] at hd
    

Proof state:
case neg
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x✝ y✝ z : α
s t : Set α
d : ℝ
x : α
hx : x ∈ s
y : α
hy : y ∈ s
hxy : x ≠ y
hd : d ≤ 0
hs : Set.Subsingleton s
⊢ d ≤ dist x y

Next tactic:
exact le_trans hd dist_nonneg
theorem infsep_pair : ({x, y} : Set α).infsep = dist x y := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x y z : α
s t : Set α
⊢ infsep {x, y} = dist x y

Next tactic:
rw [infsep_pair_eq_toReal, edist_dist]
theorem infsep_pair : ({x, y} : Set α).infsep = dist x y := by
  rw [infsep_pair_eq_toReal, edist_dist]
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x y z : α
s t : Set α
⊢ ENNReal.toReal (ENNReal.ofReal (dist x y)) = dist x y

Next tactic:
exact ENNReal.toReal_ofReal dist_nonneg
theorem infsep_triple (hxy : x ≠ y) (hyz : y ≠ z) (hxz : x ≠ z) :
    ({x, y, z} : Set α).infsep = dist x y ⊓ dist x z ⊓ dist y z := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x y z : α
s t : Set α
hxy : x ≠ y
hyz : y ≠ z
hxz : x ≠ z
⊢ infsep {x, y, z} = dist x y ⊓ dist x z ⊓ dist y z

Next tactic:
simp only [infsep, einfsep_triple hxy hyz hxz, ENNReal.toReal_inf, edist_ne_top x y,
    edist_ne_top x z, edist_ne_top y z, dist_edist, Ne.def, inf_eq_top_iff, and_self_iff,
    not_false_iff]
theorem infsep_eq_iInf [Decidable s.Nontrivial] :
    s.infsep = if s.Nontrivial then ⨅ d : s.offDiag, (uncurry dist) (d : α × α) else 0 := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝ : Decidable (Set.Nontrivial s)
⊢ infsep s = if Set.Nontrivial s then ⨅ d, uncurry dist ↑d else 0

Next tactic:
split_ifs with hs
theorem infsep_eq_iInf [Decidable s.Nontrivial] :
    s.infsep = if s.Nontrivial then ⨅ d : s.offDiag, (uncurry dist) (d : α × α) else 0 := by
  split_ifs with hs
  · 

Proof state:
case pos
α : Type u_1
β : Type u_2
inst✝¹ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝ : Decidable (Set.Nontrivial s)
hs : Set.Nontrivial s
⊢ infsep s = ⨅ d, uncurry dist ↑d

Next tactic:
have hb : BddBelow (uncurry dist '' s.offDiag) := by
      refine' ⟨0, fun d h => _⟩
      simp_rw [mem_image, Prod.exists, uncurry_apply_pair] at h
      rcases h with ⟨_, _, _, rfl⟩
      exact dist_nonneg
theorem infsep_eq_iInf [Decidable s.Nontrivial] :
    s.infsep = if s.Nontrivial then ⨅ d : s.offDiag, (uncurry dist) (d : α × α) else 0 := by
  split_ifs with hs
  · have hb : BddBelow (uncurry dist '' s.offDiag) := by
      

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝ : Decidable (Set.Nontrivial s)
hs : Set.Nontrivial s
⊢ BddBelow (uncurry dist '' offDiag s)

Next tactic:
refine' ⟨0, fun d h => _⟩
theorem infsep_eq_iInf [Decidable s.Nontrivial] :
    s.infsep = if s.Nontrivial then ⨅ d : s.offDiag, (uncurry dist) (d : α × α) else 0 := by
  split_ifs with hs
  · have hb : BddBelow (uncurry dist '' s.offDiag) := by
      refine' ⟨0, fun d h => _⟩
      

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝ : Decidable (Set.Nontrivial s)
hs : Set.Nontrivial s
d : ℝ
h : d ∈ uncurry dist '' offDiag s
⊢ 0 ≤ d

Next tactic:
simp_rw [mem_image, Prod.exists, uncurry_apply_pair] at h
theorem infsep_eq_iInf [Decidable s.Nontrivial] :
    s.infsep = if s.Nontrivial then ⨅ d : s.offDiag, (uncurry dist) (d : α × α) else 0 := by
  split_ifs with hs
  · have hb : BddBelow (uncurry dist '' s.offDiag) := by
      refine' ⟨0, fun d h => _⟩
      simp_rw [mem_image, Prod.exists, uncurry_apply_pair] at h
      

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝ : Decidable (Set.Nontrivial s)
hs : Set.Nontrivial s
d : ℝ
h : ∃ a b, (a, b) ∈ offDiag s ∧ dist a b = d
⊢ 0 ≤ d

Next tactic:
rcases h with ⟨_, _, _, rfl⟩
theorem infsep_eq_iInf [Decidable s.Nontrivial] :
    s.infsep = if s.Nontrivial then ⨅ d : s.offDiag, (uncurry dist) (d : α × α) else 0 := by
  split_ifs with hs
  · have hb : BddBelow (uncurry dist '' s.offDiag) := by
      refine' ⟨0, fun d h => _⟩
      simp_rw [mem_image, Prod.exists, uncurry_apply_pair] at h
      rcases h with ⟨_, _, _, rfl⟩
      

Proof state:
case intro.intro.intro
α : Type u_1
β : Type u_2
inst✝¹ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝ : Decidable (Set.Nontrivial s)
hs : Set.Nontrivial s
w✝¹ w✝ : α
left✝ : (w✝¹, w✝) ∈ offDiag s
⊢ 0 ≤ dist w✝¹ w✝

Next tactic:
exact dist_nonneg
theorem infsep_eq_iInf [Decidable s.Nontrivial] :
    s.infsep = if s.Nontrivial then ⨅ d : s.offDiag, (uncurry dist) (d : α × α) else 0 := by
  split_ifs with hs
  · have hb : BddBelow (uncurry dist '' s.offDiag) := by
      refine' ⟨0, fun d h => _⟩
      simp_rw [mem_image, Prod.exists, uncurry_apply_pair] at h
      rcases h with ⟨_, _, _, rfl⟩
      exact dist_nonneg
    

Proof state:
case pos
α : Type u_1
β : Type u_2
inst✝¹ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝ : Decidable (Set.Nontrivial s)
hs : Set.Nontrivial s
hb : BddBelow (uncurry dist '' offDiag s)
⊢ infsep s = ⨅ d, uncurry dist ↑d

Next tactic:
refine' eq_of_forall_le_iff fun _ => _
theorem infsep_eq_iInf [Decidable s.Nontrivial] :
    s.infsep = if s.Nontrivial then ⨅ d : s.offDiag, (uncurry dist) (d : α × α) else 0 := by
  split_ifs with hs
  · have hb : BddBelow (uncurry dist '' s.offDiag) := by
      refine' ⟨0, fun d h => _⟩
      simp_rw [mem_image, Prod.exists, uncurry_apply_pair] at h
      rcases h with ⟨_, _, _, rfl⟩
      exact dist_nonneg
    refine' eq_of_forall_le_iff fun _ => _
    

Proof state:
case pos
α : Type u_1
β : Type u_2
inst✝¹ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝ : Decidable (Set.Nontrivial s)
hs : Set.Nontrivial s
hb : BddBelow (uncurry dist '' offDiag s)
x✝ : ℝ
⊢ x✝ ≤ infsep s ↔ x✝ ≤ ⨅ d, uncurry dist ↑d

Next tactic:
simp_rw [hs.le_infsep_iff, le_ciInf_set_iff (offDiag_nonempty.mpr hs) hb, imp_forall_iff,
      mem_offDiag, Prod.forall, uncurry_apply_pair, and_imp]
theorem infsep_eq_iInf [Decidable s.Nontrivial] :
    s.infsep = if s.Nontrivial then ⨅ d : s.offDiag, (uncurry dist) (d : α × α) else 0 := by
  split_ifs with hs
  · have hb : BddBelow (uncurry dist '' s.offDiag) := by
      refine' ⟨0, fun d h => _⟩
      simp_rw [mem_image, Prod.exists, uncurry_apply_pair] at h
      rcases h with ⟨_, _, _, rfl⟩
      exact dist_nonneg
    refine' eq_of_forall_le_iff fun _ => _
    simp_rw [hs.le_infsep_iff, le_ciInf_set_iff (offDiag_nonempty.mpr hs) hb, imp_forall_iff,
      mem_offDiag, Prod.forall, uncurry_apply_pair, and_imp]
  · 

Proof state:
case neg
α : Type u_1
β : Type u_2
inst✝¹ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝ : Decidable (Set.Nontrivial s)
hs : ¬Set.Nontrivial s
⊢ infsep s = 0

Next tactic:
exact (not_nontrivial_iff.mp hs).infsep_zero
theorem Nontrivial.infsep_eq_iInf (hs : s.Nontrivial) :
    s.infsep = ⨅ d : s.offDiag, (uncurry dist) (d : α × α) := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x y z : α
s t : Set α
hs : Set.Nontrivial s
⊢ infsep s = ⨅ d, uncurry dist ↑d

Next tactic:
classical rw [Set.infsep_eq_iInf, if_pos hs]
theorem Nontrivial.infsep_eq_iInf (hs : s.Nontrivial) :
    s.infsep = ⨅ d : s.offDiag, (uncurry dist) (d : α × α) := by
  classical 

Proof state:
α : Type u_1
β : Type u_2
inst✝ : PseudoMetricSpace α
x y z : α
s t : Set α
hs : Set.Nontrivial s
⊢ infsep s = ⨅ d, uncurry dist ↑d

Next tactic:
rw [Set.infsep_eq_iInf, if_pos hs]
theorem infsep_of_fintype [Decidable s.Nontrivial] [DecidableEq α] [Fintype s] : s.infsep =
    if hs : s.Nontrivial then s.offDiag.toFinset.inf' (by 

Proof state:
α : Type u_1
β : Type u_2
inst✝³ : PseudoMetricSpace α
x y z : α
s t : Set α
inst✝² : Decidable (Set.Nontrivial s)
inst✝¹ : DecidableEq α
inst✝ : Fintype ↑s
hs : Set.Nontrivial s
⊢ Finset.Nonempty (toFinset (offDiag s))

Next tactic:
simpa