l3lab/ntp-mathlib huggingface dataset:
/-- The number of roots of a real polynomial (counted with multiplicities) is at most the number of
roots of its derivative (counted with multiplicities) plus one. -/
theorem card_roots_le_derivative (p : ℝ[X]) :
    Multiset.card p.roots ≤ Multiset.card (derivative p).roots + 1 :=
  calc
    Multiset.card p.roots = ∑ x in p.roots.toFinset, p.roots.count x :=
      (Multiset.toFinset_sum_count_eq _).symm
    _ = ∑ x in p.roots.toFinset, (p.roots.count x - 1 + 1) :=
      (Eq.symm <| Finset.sum_congr rfl fun x hx => tsub_add_cancel_of_le <|
        Nat.succ_le_iff.2 <| Multiset.count_pos.2 <| Multiset.mem_toFinset.1 hx)
    _ = (∑ x in p.roots.toFinset, (p.rootMultiplicity x - 1)) + p.roots.toFinset.card := by
      simp only [Finset.sum_add_distrib, Finset.card_eq_sum_ones, count_roots]
    _ ≤ (∑ x in p.roots.toFinset, p.derivative.rootMultiplicity x) +
          ((p.derivative.roots.toFinset \ p.roots.toFinset).card + 1) :=
      (add_le_add
        (Finset.sum_le_sum fun x _ => rootMultiplicity_sub_one_le_derivative_rootMultiplicity _ _)
        p.card_roots_toFinset_le_card_roots_derivative_diff_roots_succ)
    _ ≤ (∑ x in p.roots.toFinset, p.derivative.roots.count x) +
          ((∑ x in p.derivative.roots.toFinset \ p.roots.toFinset,
            p.derivative.roots.count x) + 1) := by
      simp only [← count_roots]
      refine' add_le_add_left (add_le_add_right ((Finset.card_eq_sum_ones _).trans_le _) _) _
      refine' Finset.sum_le_sum fun x hx => Nat.succ_le_iff.2 <| _
      rw [Multiset.count_pos, ← Multiset.mem_toFinset]
      

Proof state:
p : ℝ[X]
x : ℝ
hx : x ∈ Multiset.toFinset (roots (derivative p)) \ Multiset.toFinset (roots p)
⊢ x ∈ Multiset.toFinset (roots (derivative p))

Next tactic:
exact (Finset.mem_sdiff.1 hx).1
/-- The number of roots of a real polynomial (counted with multiplicities) is at most the number of
roots of its derivative (counted with multiplicities) plus one. -/
theorem card_roots_le_derivative (p : ℝ[X]) :
    Multiset.card p.roots ≤ Multiset.card (derivative p).roots + 1 :=
  calc
    Multiset.card p.roots = ∑ x in p.roots.toFinset, p.roots.count x :=
      (Multiset.toFinset_sum_count_eq _).symm
    _ = ∑ x in p.roots.toFinset, (p.roots.count x - 1 + 1) :=
      (Eq.symm <| Finset.sum_congr rfl fun x hx => tsub_add_cancel_of_le <|
        Nat.succ_le_iff.2 <| Multiset.count_pos.2 <| Multiset.mem_toFinset.1 hx)
    _ = (∑ x in p.roots.toFinset, (p.rootMultiplicity x - 1)) + p.roots.toFinset.card := by
      simp only [Finset.sum_add_distrib, Finset.card_eq_sum_ones, count_roots]
    _ ≤ (∑ x in p.roots.toFinset, p.derivative.rootMultiplicity x) +
          ((p.derivative.roots.toFinset \ p.roots.toFinset).card + 1) :=
      (add_le_add
        (Finset.sum_le_sum fun x _ => rootMultiplicity_sub_one_le_derivative_rootMultiplicity _ _)
        p.card_roots_toFinset_le_card_roots_derivative_diff_roots_succ)
    _ ≤ (∑ x in p.roots.toFinset, p.derivative.roots.count x) +
          ((∑ x in p.derivative.roots.toFinset \ p.roots.toFinset,
            p.derivative.roots.count x) + 1) := by
      simp only [← count_roots]
      refine' add_le_add_left (add_le_add_right ((Finset.card_eq_sum_ones _).trans_le _) _) _
      refine' Finset.sum_le_sum fun x hx => Nat.succ_le_iff.2 <| _
      rw [Multiset.count_pos, ← Multiset.mem_toFinset]
      exact (Finset.mem_sdiff.1 hx).1
    _ = Multiset.card (derivative p).roots + 1 := by
      

Proof state:
p : ℝ[X]
⊢ ∑ x in Multiset.toFinset (roots p), Multiset.count x (roots (derivative p)) +
      (∑ x in Multiset.toFinset (roots (derivative p)) \ Multiset.toFinset (roots p),
          Multiset.count x (roots (derivative p)) +
        1) =
    Multiset.card (roots (derivative p)) + 1

Next tactic:
rw [← add_assoc, ← Finset.sum_union Finset.disjoint_sdiff, Finset.union_sdiff_self_eq_union, ←
        Multiset.toFinset_sum_count_eq, ← Finset.sum_subset (Finset.subset_union_right _ _)]
/-- The number of roots of a real polynomial (counted with multiplicities) is at most the number of
roots of its derivative (counted with multiplicities) plus one. -/
theorem card_roots_le_derivative (p : ℝ[X]) :
    Multiset.card p.roots ≤ Multiset.card (derivative p).roots + 1 :=
  calc
    Multiset.card p.roots = ∑ x in p.roots.toFinset, p.roots.count x :=
      (Multiset.toFinset_sum_count_eq _).symm
    _ = ∑ x in p.roots.toFinset, (p.roots.count x - 1 + 1) :=
      (Eq.symm <| Finset.sum_congr rfl fun x hx => tsub_add_cancel_of_le <|
        Nat.succ_le_iff.2 <| Multiset.count_pos.2 <| Multiset.mem_toFinset.1 hx)
    _ = (∑ x in p.roots.toFinset, (p.rootMultiplicity x - 1)) + p.roots.toFinset.card := by
      simp only [Finset.sum_add_distrib, Finset.card_eq_sum_ones, count_roots]
    _ ≤ (∑ x in p.roots.toFinset, p.derivative.rootMultiplicity x) +
          ((p.derivative.roots.toFinset \ p.roots.toFinset).card + 1) :=
      (add_le_add
        (Finset.sum_le_sum fun x _ => rootMultiplicity_sub_one_le_derivative_rootMultiplicity _ _)
        p.card_roots_toFinset_le_card_roots_derivative_diff_roots_succ)
    _ ≤ (∑ x in p.roots.toFinset, p.derivative.roots.count x) +
          ((∑ x in p.derivative.roots.toFinset \ p.roots.toFinset,
            p.derivative.roots.count x) + 1) := by
      simp only [← count_roots]
      refine' add_le_add_left (add_le_add_right ((Finset.card_eq_sum_ones _).trans_le _) _) _
      refine' Finset.sum_le_sum fun x hx => Nat.succ_le_iff.2 <| _
      rw [Multiset.count_pos, ← Multiset.mem_toFinset]
      exact (Finset.mem_sdiff.1 hx).1
    _ = Multiset.card (derivative p).roots + 1 := by
      rw [← add_assoc, ← Finset.sum_union Finset.disjoint_sdiff, Finset.union_sdiff_self_eq_union, ←
        Multiset.toFinset_sum_count_eq, ← Finset.sum_subset (Finset.subset_union_right _ _)]
      

Proof state:
p : ℝ[X]
⊢ ∀ x ∈ Multiset.toFinset (roots p) ∪ Multiset.toFinset (roots (derivative p)),
    x ∉ Multiset.toFinset (roots (derivative p)) → Multiset.count x (roots (derivative p)) = 0

Next tactic:
intro x _ hx₂
/-- The number of roots of a real polynomial (counted with multiplicities) is at most the number of
roots of its derivative (counted with multiplicities) plus one. -/
theorem card_roots_le_derivative (p : ℝ[X]) :
    Multiset.card p.roots ≤ Multiset.card (derivative p).roots + 1 :=
  calc
    Multiset.card p.roots = ∑ x in p.roots.toFinset, p.roots.count x :=
      (Multiset.toFinset_sum_count_eq _).symm
    _ = ∑ x in p.roots.toFinset, (p.roots.count x - 1 + 1) :=
      (Eq.symm <| Finset.sum_congr rfl fun x hx => tsub_add_cancel_of_le <|
        Nat.succ_le_iff.2 <| Multiset.count_pos.2 <| Multiset.mem_toFinset.1 hx)
    _ = (∑ x in p.roots.toFinset, (p.rootMultiplicity x - 1)) + p.roots.toFinset.card := by
      simp only [Finset.sum_add_distrib, Finset.card_eq_sum_ones, count_roots]
    _ ≤ (∑ x in p.roots.toFinset, p.derivative.rootMultiplicity x) +
          ((p.derivative.roots.toFinset \ p.roots.toFinset).card + 1) :=
      (add_le_add
        (Finset.sum_le_sum fun x _ => rootMultiplicity_sub_one_le_derivative_rootMultiplicity _ _)
        p.card_roots_toFinset_le_card_roots_derivative_diff_roots_succ)
    _ ≤ (∑ x in p.roots.toFinset, p.derivative.roots.count x) +
          ((∑ x in p.derivative.roots.toFinset \ p.roots.toFinset,
            p.derivative.roots.count x) + 1) := by
      simp only [← count_roots]
      refine' add_le_add_left (add_le_add_right ((Finset.card_eq_sum_ones _).trans_le _) _) _
      refine' Finset.sum_le_sum fun x hx => Nat.succ_le_iff.2 <| _
      rw [Multiset.count_pos, ← Multiset.mem_toFinset]
      exact (Finset.mem_sdiff.1 hx).1
    _ = Multiset.card (derivative p).roots + 1 := by
      rw [← add_assoc, ← Finset.sum_union Finset.disjoint_sdiff, Finset.union_sdiff_self_eq_union, ←
        Multiset.toFinset_sum_count_eq, ← Finset.sum_subset (Finset.subset_union_right _ _)]
      intro x _ hx₂
      

Proof state:
p : ℝ[X]
x : ℝ
a✝ : x ∈ Multiset.toFinset (roots p) ∪ Multiset.toFinset (roots (derivative p))
hx₂ : x ∉ Multiset.toFinset (roots (derivative p))
⊢ Multiset.count x (roots (derivative p)) = 0

Next tactic:
simpa only [Multiset.mem_toFinset, Multiset.count_eq_zero] using hx₂
/-- The number of real roots of a polynomial is at most the number of roots of its derivative plus
one. -/
theorem card_rootSet_le_derivative {F : Type*} [CommRing F] [Algebra F ℝ] (p : F[X]) :
    Fintype.card (p.rootSet ℝ) ≤ Fintype.card (p.derivative.rootSet ℝ) + 1 := by
  

Proof state:
F : Type u_1
inst✝¹ : CommRing F
inst✝ : Algebra F ℝ
p : F[X]
⊢ Fintype.card ↑(rootSet p ℝ) ≤ Fintype.card ↑(rootSet (derivative p) ℝ) + 1

Next tactic:
simpa only [rootSet_def, Finset.coe_sort_coe, Fintype.card_coe, derivative_map] using
    card_roots_toFinset_le_derivative (p.map (algebraMap F ℝ))
@[simp]
theorem sup_add (s₁ s₂ : Multiset α) : (s₁ + s₂).sup = s₁.sup ⊔ s₂.sup :=
  Eq.trans (by 

Proof state:
α : Type u_1
inst✝¹ : SemilatticeSup α
inst✝ : OrderBot α
s₁ s₂ : Multiset α
⊢ sup (s₁ + s₂) = fold (fun x x_1 => x ⊔ x_1) (⊥ ⊔ ⊥) (s₁ + s₂)

Next tactic:
simp [sup]
@[simp]
theorem sup_le {s : Multiset α} {a : α} : s.sup ≤ a ↔ ∀ b ∈ s, b ≤ a :=
  Multiset.induction_on s (by 

Proof state:
α : Type u_1
inst✝¹ : SemilatticeSup α
inst✝ : OrderBot α
s : Multiset α
a : α
⊢ sup 0 ≤ a ↔ ∀ b ∈ 0, b ≤ a

Next tactic:
simp
@[simp]
theorem sup_le {s : Multiset α} {a : α} : s.sup ≤ a ↔ ∀ b ∈ s, b ≤ a :=
  Multiset.induction_on s (by simp)
    (by 

Proof state:
α : Type u_1
inst✝¹ : SemilatticeSup α
inst✝ : OrderBot α
s : Multiset α
a : α
⊢ ∀ ⦃a_1 : α⦄ {s : Multiset α}, (sup s ≤ a ↔ ∀ b ∈ s, b ≤ a) → (sup (a_1 ::ₘ s) ≤ a ↔ ∀ b ∈ a_1 ::ₘ s, b ≤ a)

Next tactic:
simp (config := { contextual := true }) [or_imp, forall_and]
@[simp]
theorem sup_ndunion (s₁ s₂ : Multiset α) : (ndunion s₁ s₂).sup = s₁.sup ⊔ s₂.sup := by
  

Proof state:
α : Type u_1
inst✝² : SemilatticeSup α
inst✝¹ : OrderBot α
inst✝ : DecidableEq α
s₁ s₂ : Multiset α
⊢ sup (ndunion s₁ s₂) = sup s₁ ⊔ sup s₂

Next tactic:
rw [← sup_dedup, dedup_ext.2, sup_dedup, sup_add]
@[simp]
theorem sup_ndunion (s₁ s₂ : Multiset α) : (ndunion s₁ s₂).sup = s₁.sup ⊔ s₂.sup := by
  rw [← sup_dedup, dedup_ext.2, sup_dedup, sup_add]; 

Proof state:
α : Type u_1
inst✝² : SemilatticeSup α
inst✝¹ : OrderBot α
inst✝ : DecidableEq α
s₁ s₂ : Multiset α
⊢ ∀ (a : α), a ∈ ndunion s₁ s₂ ↔ a ∈ s₁ + s₂

Next tactic:
simp
@[simp]
theorem sup_union (s₁ s₂ : Multiset α) : (s₁ ∪ s₂).sup = s₁.sup ⊔ s₂.sup := by
  

Proof state:
α : Type u_1
inst✝² : SemilatticeSup α
inst✝¹ : OrderBot α
inst✝ : DecidableEq α
s₁ s₂ : Multiset α
⊢ sup (s₁ ∪ s₂) = sup s₁ ⊔ sup s₂

Next tactic:
rw [← sup_dedup, dedup_ext.2, sup_dedup, sup_add]
@[simp]
theorem sup_union (s₁ s₂ : Multiset α) : (s₁ ∪ s₂).sup = s₁.sup ⊔ s₂.sup := by
  rw [← sup_dedup, dedup_ext.2, sup_dedup, sup_add]; 

Proof state:
α : Type u_1
inst✝² : SemilatticeSup α
inst✝¹ : OrderBot α
inst✝ : DecidableEq α
s₁ s₂ : Multiset α
⊢ ∀ (a : α), a ∈ s₁ ∪ s₂ ↔ a ∈ s₁ + s₂

Next tactic:
simp
@[simp]
theorem sup_ndinsert (a : α) (s : Multiset α) : (ndinsert a s).sup = a ⊔ s.sup := by
  

Proof state:
α : Type u_1
inst✝² : SemilatticeSup α
inst✝¹ : OrderBot α
inst✝ : DecidableEq α
a : α
s : Multiset α
⊢ sup (ndinsert a s) = a ⊔ sup s

Next tactic:
rw [← sup_dedup, dedup_ext.2, sup_dedup, sup_cons]
@[simp]
theorem sup_ndinsert (a : α) (s : Multiset α) : (ndinsert a s).sup = a ⊔ s.sup := by
  rw [← sup_dedup, dedup_ext.2, sup_dedup, sup_cons]; 

Proof state:
α : Type u_1
inst✝² : SemilatticeSup α
inst✝¹ : OrderBot α
inst✝ : DecidableEq α
a : α
s : Multiset α
⊢ ∀ (a_1 : α), a_1 ∈ ndinsert a s ↔ a_1 ∈ a ::ₘ s

Next tactic:
simp
theorem nodup_sup_iff {α : Type*} [DecidableEq α] {m : Multiset (Multiset α)} :
    m.sup.Nodup ↔ ∀ a : Multiset α, a ∈ m → a.Nodup := by
  -- Porting note: this was originally `apply m.induction_on`, which failed due to
  -- `failed to elaborate eliminator, expected type is not available`
  

Proof state:
α✝ : Type u_1
inst✝³ : SemilatticeSup α✝
inst✝² : OrderBot α✝
inst✝¹ : DecidableEq α✝
α : Type u_2
inst✝ : DecidableEq α
m : Multiset (Multiset α)
⊢ Nodup (sup m) ↔ ∀ a ∈ m, Nodup a

Next tactic:
induction' m using Multiset.induction_on with _ _ h
theorem nodup_sup_iff {α : Type*} [DecidableEq α] {m : Multiset (Multiset α)} :
    m.sup.Nodup ↔ ∀ a : Multiset α, a ∈ m → a.Nodup := by
  -- Porting note: this was originally `apply m.induction_on`, which failed due to
  -- `failed to elaborate eliminator, expected type is not available`
  induction' m using Multiset.induction_on with _ _ h
  · 

Proof state:
case empty
α✝ : Type u_1
inst✝³ : SemilatticeSup α✝
inst✝² : OrderBot α✝
inst✝¹ : DecidableEq α✝
α : Type u_2
inst✝ : DecidableEq α
⊢ Nodup (sup 0) ↔ ∀ a ∈ 0, Nodup a

Next tactic:
simp
theorem nodup_sup_iff {α : Type*} [DecidableEq α] {m : Multiset (Multiset α)} :
    m.sup.Nodup ↔ ∀ a : Multiset α, a ∈ m → a.Nodup := by
  -- Porting note: this was originally `apply m.induction_on`, which failed due to
  -- `failed to elaborate eliminator, expected type is not available`
  induction' m using Multiset.induction_on with _ _ h
  · simp
  · 

Proof state:
case cons
α✝ : Type u_1
inst✝³ : SemilatticeSup α✝
inst✝² : OrderBot α✝
inst✝¹ : DecidableEq α✝
α : Type u_2
inst✝ : DecidableEq α
a✝ : Multiset α
s✝ : Multiset (Multiset α)
h : Nodup (sup s✝) ↔ ∀ a ∈ s✝, Nodup a
⊢ Nodup (sup (a✝ ::ₘ s✝)) ↔ ∀ a ∈ a✝ ::ₘ s✝, Nodup a

Next tactic:
simp [h]
@[simp]
theorem inf_add (s₁ s₂ : Multiset α) : (s₁ + s₂).inf = s₁.inf ⊓ s₂.inf :=
  Eq.trans (by 

Proof state:
α : Type u_1
inst✝¹ : SemilatticeInf α
inst✝ : OrderTop α
s₁ s₂ : Multiset α
⊢ inf (s₁ + s₂) = fold (fun x x_1 => x ⊓ x_1) (⊤ ⊓ ⊤) (s₁ + s₂)

Next tactic:
simp [inf]
@[simp]
theorem le_inf {s : Multiset α} {a : α} : a ≤ s.inf ↔ ∀ b ∈ s, a ≤ b :=
  Multiset.induction_on s (by 

Proof state:
α : Type u_1
inst✝¹ : SemilatticeInf α
inst✝ : OrderTop α
s : Multiset α
a : α
⊢ a ≤ inf 0 ↔ ∀ b ∈ 0, a ≤ b

Next tactic:
simp
@[simp]
theorem le_inf {s : Multiset α} {a : α} : a ≤ s.inf ↔ ∀ b ∈ s, a ≤ b :=
  Multiset.induction_on s (by simp)
    (by 

Proof state:
α : Type u_1
inst✝¹ : SemilatticeInf α
inst✝ : OrderTop α
s : Multiset α
a : α
⊢ ∀ ⦃a_1 : α⦄ {s : Multiset α}, (a ≤ inf s ↔ ∀ b ∈ s, a ≤ b) → (a ≤ inf (a_1 ::ₘ s) ↔ ∀ b ∈ a_1 ::ₘ s, a ≤ b)

Next tactic:
simp (config := { contextual := true }) [or_imp, forall_and]
@[simp]
theorem inf_ndunion (s₁ s₂ : Multiset α) : (ndunion s₁ s₂).inf = s₁.inf ⊓ s₂.inf := by
  

Proof state:
α : Type u_1
inst✝² : SemilatticeInf α
inst✝¹ : OrderTop α
inst✝ : DecidableEq α
s₁ s₂ : Multiset α
⊢ inf (ndunion s₁ s₂) = inf s₁ ⊓ inf s₂

Next tactic:
rw [← inf_dedup, dedup_ext.2, inf_dedup, inf_add]
@[simp]
theorem inf_ndunion (s₁ s₂ : Multiset α) : (ndunion s₁ s₂).inf = s₁.inf ⊓ s₂.inf := by
  rw [← inf_dedup, dedup_ext.2, inf_dedup, inf_add]; 

Proof state:
α : Type u_1
inst✝² : SemilatticeInf α
inst✝¹ : OrderTop α
inst✝ : DecidableEq α
s₁ s₂ : Multiset α
⊢ ∀ (a : α), a ∈ ndunion s₁ s₂ ↔ a ∈ s₁ + s₂

Next tactic:
simp
@[simp]
theorem inf_union (s₁ s₂ : Multiset α) : (s₁ ∪ s₂).inf = s₁.inf ⊓ s₂.inf := by
  

Proof state:
α : Type u_1
inst✝² : SemilatticeInf α
inst✝¹ : OrderTop α
inst✝ : DecidableEq α
s₁ s₂ : Multiset α
⊢ inf (s₁ ∪ s₂) = inf s₁ ⊓ inf s₂

Next tactic:
rw [← inf_dedup, dedup_ext.2, inf_dedup, inf_add]
@[simp]
theorem inf_union (s₁ s₂ : Multiset α) : (s₁ ∪ s₂).inf = s₁.inf ⊓ s₂.inf := by
  rw [← inf_dedup, dedup_ext.2, inf_dedup, inf_add]; 

Proof state:
α : Type u_1
inst✝² : SemilatticeInf α
inst✝¹ : OrderTop α
inst✝ : DecidableEq α
s₁ s₂ : Multiset α
⊢ ∀ (a : α), a ∈ s₁ ∪ s₂ ↔ a ∈ s₁ + s₂

Next tactic:
simp
@[simp]
theorem inf_ndinsert (a : α) (s : Multiset α) : (ndinsert a s).inf = a ⊓ s.inf := by
  

Proof state:
α : Type u_1
inst✝² : SemilatticeInf α
inst✝¹ : OrderTop α
inst✝ : DecidableEq α
a : α
s : Multiset α
⊢ inf (ndinsert a s) = a ⊓ inf s

Next tactic:
rw [← inf_dedup, dedup_ext.2, inf_dedup, inf_cons]
@[simp]
theorem inf_ndinsert (a : α) (s : Multiset α) : (ndinsert a s).inf = a ⊓ s.inf := by
  rw [← inf_dedup, dedup_ext.2, inf_dedup, inf_cons]; 

Proof state:
α : Type u_1
inst✝² : SemilatticeInf α
inst✝¹ : OrderTop α
inst✝ : DecidableEq α
a : α
s : Multiset α
⊢ ∀ (a_1 : α), a_1 ∈ ndinsert a s ↔ a_1 ∈ a ::ₘ s

Next tactic:
simp
@[simp]
lemma uIcc_of_le (h : a ≤ b) : [[a, b]] = Icc a b := by 

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : Lattice α
inst✝ : Lattice β
a a₁ a₂ b b₁ b₂ c x : α
h : a ≤ b
⊢ [[a, b]] = Icc a b

Next tactic:
rw [uIcc, inf_eq_left.2 h, sup_eq_right.2 h]
@[simp]
lemma uIcc_of_ge (h : b ≤ a) : [[a, b]] = Icc b a := by 

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : Lattice α
inst✝ : Lattice β
a a₁ a₂ b b₁ b₂ c x : α
h : b ≤ a
⊢ [[a, b]] = Icc b a

Next tactic:
rw [uIcc, inf_eq_right.2 h, sup_eq_left.2 h]
lemma uIcc_comm (a b : α) : [[a, b]] = [[b, a]] := by 

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : Lattice α
inst✝ : Lattice β
a✝ a₁ a₂ b✝ b₁ b₂ c x a b : α
⊢ [[a, b]] = [[b, a]]

Next tactic:
simp_rw [uIcc, inf_comm, sup_comm]
lemma uIcc_self : [[a, a]] = {a} := by 

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : Lattice α
inst✝ : Lattice β
a a₁ a₂ b b₁ b₂ c x : α
⊢ [[a, a]] = {a}

Next tactic:
simp [uIcc]
theorem uIcc_prod_eq (a b : α × β) : [[a, b]] = [[a.1, b.1]] ×ˢ [[a.2, b.2]] := by 

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : Lattice α
inst✝ : Lattice β
a✝ a₁ a₂ b✝ b₁ b₂ c x : α
a b : α × β
⊢ [[a, b]] = [[a.1, b.1]] ×ˢ [[a.2, b.2]]

Next tactic:
simp
lemma eq_of_mem_uIcc_of_mem_uIcc' : b ∈ [[a, c]] → c ∈ [[a, b]] → b = c := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : DistribLattice α
a a₁ a₂ b b₁ b₂ c x : α
⊢ b ∈ [[a, c]] → c ∈ [[a, b]] → b = c

Next tactic:
simpa only [uIcc_comm a] using eq_of_mem_uIcc_of_mem_uIcc
lemma uIcc_injective_right (a : α) : Injective fun b => uIcc b a := fun b c h => by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : DistribLattice α
a✝ a₁ a₂ b✝ b₁ b₂ c✝ x a b c : α
h : (fun b => [[b, a]]) b = (fun b => [[b, a]]) c
⊢ b = c

Next tactic:
rw [ext_iff] at h
lemma uIcc_injective_right (a : α) : Injective fun b => uIcc b a := fun b c h => by
  rw [ext_iff] at h
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : DistribLattice α
a✝ a₁ a₂ b✝ b₁ b₂ c✝ x a b c : α
h : ∀ (x : α), x ∈ (fun b => [[b, a]]) b ↔ x ∈ (fun b => [[b, a]]) c
⊢ b = c

Next tactic:
exact eq_of_mem_uIcc_of_mem_uIcc ((h _).1 left_mem_uIcc) ((h _).2 left_mem_uIcc)
lemma uIcc_injective_left (a : α) : Injective (uIcc a) := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝ : DistribLattice α
a✝ a₁ a₂ b b₁ b₂ c x a : α
⊢ Injective (uIcc a)

Next tactic:
simpa only [uIcc_comm] using uIcc_injective_right a
lemma _root_.MonotoneOn.mapsTo_uIcc (hf : MonotoneOn f (uIcc a b)) :
    MapsTo f (uIcc a b) (uIcc (f a) (f b)) := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : Lattice β
f : α → β
s : Set α
a b : α
hf : MonotoneOn f [[a, b]]
⊢ MapsTo f [[a, b]] [[f a, f b]]

Next tactic:
rw [uIcc, uIcc, ← hf.map_sup, ← hf.map_inf]
lemma _root_.MonotoneOn.mapsTo_uIcc (hf : MonotoneOn f (uIcc a b)) :
    MapsTo f (uIcc a b) (uIcc (f a) (f b)) := by
  rw [uIcc, uIcc, ← hf.map_sup, ← hf.map_inf] <;>
    

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : Lattice β
f : α → β
s : Set α
a b : α
hf : MonotoneOn f [[a, b]]
⊢ MapsTo f (Icc (a ⊓ b) (a ⊔ b)) (Icc (f (a ⊓ b)) (f (a ⊔ b)))

Next tactic:
apply_rules [left_mem_uIcc, right_mem_uIcc, hf.mapsTo_Icc]
lemma _root_.MonotoneOn.mapsTo_uIcc (hf : MonotoneOn f (uIcc a b)) :
    MapsTo f (uIcc a b) (uIcc (f a) (f b)) := by
  rw [uIcc, uIcc, ← hf.map_sup, ← hf.map_inf] <;>
    

Proof state:
case hx
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : Lattice β
f : α → β
s : Set α
a b : α
hf : MonotoneOn f [[a, b]]
⊢ a ∈ [[a, b]]

Next tactic:
apply_rules [left_mem_uIcc, right_mem_uIcc, hf.mapsTo_Icc]
lemma _root_.MonotoneOn.mapsTo_uIcc (hf : MonotoneOn f (uIcc a b)) :
    MapsTo f (uIcc a b) (uIcc (f a) (f b)) := by
  rw [uIcc, uIcc, ← hf.map_sup, ← hf.map_inf] <;>
    

Proof state:
case hy
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : Lattice β
f : α → β
s : Set α
a b : α
hf : MonotoneOn f [[a, b]]
⊢ b ∈ [[a, b]]

Next tactic:
apply_rules [left_mem_uIcc, right_mem_uIcc, hf.mapsTo_Icc]
lemma _root_.AntitoneOn.mapsTo_uIcc (hf : AntitoneOn f (uIcc a b)) :
    MapsTo f (uIcc a b) (uIcc (f a) (f b)) := by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : Lattice β
f : α → β
s : Set α
a b : α
hf : AntitoneOn f [[a, b]]
⊢ MapsTo f [[a, b]] [[f a, f b]]

Next tactic:
rw [uIcc, uIcc, ← hf.map_sup, ← hf.map_inf]
lemma _root_.AntitoneOn.mapsTo_uIcc (hf : AntitoneOn f (uIcc a b)) :
    MapsTo f (uIcc a b) (uIcc (f a) (f b)) := by
  rw [uIcc, uIcc, ← hf.map_sup, ← hf.map_inf] <;>
    

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : Lattice β
f : α → β
s : Set α
a b : α
hf : AntitoneOn f [[a, b]]
⊢ MapsTo f (Icc (a ⊓ b) (a ⊔ b)) (Icc (f (a ⊔ b)) (f (a ⊓ b)))

Next tactic:
apply_rules [left_mem_uIcc, right_mem_uIcc, hf.mapsTo_Icc]
lemma _root_.AntitoneOn.mapsTo_uIcc (hf : AntitoneOn f (uIcc a b)) :
    MapsTo f (uIcc a b) (uIcc (f a) (f b)) := by
  rw [uIcc, uIcc, ← hf.map_sup, ← hf.map_inf] <;>
    

Proof state:
case hx
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : Lattice β
f : α → β
s : Set α
a b : α
hf : AntitoneOn f [[a, b]]
⊢ a ∈ [[a, b]]

Next tactic:
apply_rules [left_mem_uIcc, right_mem_uIcc, hf.mapsTo_Icc]
lemma _root_.AntitoneOn.mapsTo_uIcc (hf : AntitoneOn f (uIcc a b)) :
    MapsTo f (uIcc a b) (uIcc (f a) (f b)) := by
  rw [uIcc, uIcc, ← hf.map_sup, ← hf.map_inf] <;>
    

Proof state:
case hy
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : Lattice β
f : α → β
s : Set α
a b : α
hf : AntitoneOn f [[a, b]]
⊢ b ∈ [[a, b]]

Next tactic:
apply_rules [left_mem_uIcc, right_mem_uIcc, hf.mapsTo_Icc]
lemma uIcc_eq_union : [[a, b]] = Icc a b ∪ Icc b a := by 

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : α → β
s : Set α
a a₁ a₂ b b₁ b₂ c d x : α
⊢ [[a, b]] = Icc a b ∪ Icc b a

Next tactic:
rw [Icc_union_Icc', max_comm]
lemma uIcc_eq_union : [[a, b]] = Icc a b ∪ Icc b a := by rw [Icc_union_Icc', max_comm] <;> 

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : α → β
s : Set α
a a₁ a₂ b b₁ b₂ c d x : α
⊢ [[a, b]] = Icc (min a b) (max a b)

Next tactic:
rfl
lemma uIcc_eq_union : [[a, b]] = Icc a b ∪ Icc b a := by rw [Icc_union_Icc', max_comm] <;> 

Proof state:
case h₁
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : α → β
s : Set α
a a₁ a₂ b b₁ b₂ c d x : α
⊢ b ≤ b

Next tactic:
rfl
lemma uIcc_eq_union : [[a, b]] = Icc a b ∪ Icc b a := by rw [Icc_union_Icc', max_comm] <;> 

Proof state:
case h₂
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : α → β
s : Set α
a a₁ a₂ b b₁ b₂ c d x : α
⊢ a ≤ a

Next tactic:
rfl
lemma mem_uIcc : a ∈ [[b, c]] ↔ b ≤ a ∧ a ≤ c ∨ c ≤ a ∧ a ≤ b := by 

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : α → β
s : Set α
a a₁ a₂ b b₁ b₂ c d x : α
⊢ a ∈ [[b, c]] ↔ b ≤ a ∧ a ≤ c ∨ c ≤ a ∧ a ≤ b

Next tactic:
simp [uIcc_eq_union]
/-- A sort of triangle inequality. -/
lemma uIcc_subset_uIcc_union_uIcc : [[a, c]] ⊆ [[a, b]] ∪ [[b, c]] := fun x => by
  

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : α → β
s : Set α
a a₁ a₂ b b₁ b₂ c d x✝ x : α
⊢ x ∈ [[a, c]] → x ∈ [[a, b]] ∪ [[b, c]]

Next tactic:
simp only [mem_uIcc, mem_union]
/-- A sort of triangle inequality. -/
lemma uIcc_subset_uIcc_union_uIcc : [[a, c]] ⊆ [[a, b]] ∪ [[b, c]] := fun x => by
  simp only [mem_uIcc, mem_union]
  

Proof state:
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : α → β
s : Set α
a a₁ a₂ b b₁ b₂ c d x✝ x : α
⊢ a ≤ x ∧ x ≤ c ∨ c ≤ x ∧ x ≤ a → (a ≤ x ∧ x ≤ b ∨ b ≤ x ∧ x ≤ a) ∨ b ≤ x ∧ x ≤ c ∨ c ≤ x ∧ x ≤ b

Next tactic:
rcases le_total x b with h2 | h2
/-- A sort of triangle inequality. -/
lemma uIcc_subset_uIcc_union_uIcc : [[a, c]] ⊆ [[a, b]] ∪ [[b, c]] := fun x => by
  simp only [mem_uIcc, mem_union]
  rcases le_total x b with h2 | h2 <;> 

Proof state:
case inl
α : Type u_1
β : Type u_2
inst✝¹ : LinearOrder α
inst✝ : LinearOrder β
f : α → β
s : Set α
a a₁ a₂ b b₁ b₂ c d x✝ x : α
h2 : x ≤ b
⊢ a ≤ x ∧ x ≤ c ∨ c ≤ x ∧ x ≤ a → (a ≤ x ∧ x ≤ b ∨ b ≤ x ∧ x ≤ a) ∨ b ≤ x ∧ x ≤ c ∨ c ≤ x ∧ x ≤ b

Next tactic:
tauto