l3lab/ntp-mathlib huggingface dataset:
theorem add_powHalf_succ_self_eq_powHalf (n) : powHalf (n + 1) + powHalf (n + 1) ≈ powHalf n := by
  induction' n using Nat.strong_induction_on with n hn
  · constructor <;> rw [le_iff_forall_lf] <;> constructor
    · rintro (⟨⟨⟩⟩ | ⟨⟨⟩⟩) <;> apply lf_of_lt
      · calc
          0 + powHalf n.succ ≈ powHalf n.succ := zero_add_equiv _
          _ < powHalf n := powHalf_succ_lt_powHalf n
      · calc
          powHalf n.succ + 0 ≈ powHalf n.succ := add_zero_equiv _
          _ < powHalf n := powHalf_succ_lt_powHalf n
    · cases' n with n
      · rintro ⟨⟩
      rintro ⟨⟩
      apply lf_of_moveRight_le
      swap; exact Sum.inl default
      calc
        powHalf n.succ + powHalf (n.succ + 1) ≤ powHalf n.succ + powHalf n.succ :=
          add_le_add_left (powHalf_succ_le_powHalf _) _
        _ ≈ powHalf n := hn _ (Nat.lt_succ_self n)
    · simp only [powHalf_moveLeft, forall_const]
      apply lf_of_lt
      calc
        0 ≈ 0 + 0 := (Equiv.symm (add_zero_equiv 0))
        _ ≤ powHalf n.succ + 0 := (add_le_add_right (zero_le_powHalf _) _)
        _ < powHalf n.succ + powHalf n.succ := add_lt_add_left (powHalf_pos _) _
    · rintro (⟨⟨⟩⟩ | ⟨⟨⟩⟩) <;> apply lf_of_lt
      · calc
          powHalf n ≈ powHalf n + 0 := (Equiv.symm (add_zero_equiv _))
          _ < powHalf n + powHalf n.succ := add_lt_add_left (powHalf_pos _) _
      · 

Proof state:
case h.right.right.inr.unit.h
n : ℕ
hn : ∀ m < n, powHalf (m + 1) + powHalf (m + 1) ≈ powHalf m
⊢ powHalf n < moveRight (powHalf (n + 1) + powHalf (n + 1)) (Sum.inr PUnit.unit)

Next tactic:
calc
          powHalf n ≈ 0 + powHalf n := (Equiv.symm (zero_add_equiv _))
          _ < powHalf n.succ + powHalf n := add_lt_add_right (powHalf_pos _) _
@[simp]
theorem double_powHalf_succ_eq_powHalf (n : ℕ) : 2 • powHalf n.succ = powHalf n := by
  

Proof state:
n : ℕ
⊢ 2 • powHalf (Nat.succ n) = powHalf n

Next tactic:
rw [two_nsmul]
@[simp]
theorem double_powHalf_succ_eq_powHalf (n : ℕ) : 2 • powHalf n.succ = powHalf n := by
  rw [two_nsmul]; 

Proof state:
n : ℕ
⊢ powHalf (Nat.succ n) + powHalf (Nat.succ n) = powHalf n

Next tactic:
exact Quotient.sound (PGame.add_powHalf_succ_self_eq_powHalf n)
@[simp]
theorem nsmul_pow_two_powHalf (n : ℕ) : 2 ^ n • powHalf n = 1 := by
  

Proof state:
n : ℕ
⊢ 2 ^ n • powHalf n = 1

Next tactic:
induction' n with n hn
@[simp]
theorem nsmul_pow_two_powHalf (n : ℕ) : 2 ^ n • powHalf n = 1 := by
  induction' n with n hn
  · 

Proof state:
case zero
⊢ 2 ^ Nat.zero • powHalf Nat.zero = 1

Next tactic:
simp only [Nat.zero_eq, pow_zero, powHalf_zero, one_smul]
@[simp]
theorem nsmul_pow_two_powHalf (n : ℕ) : 2 ^ n • powHalf n = 1 := by
  induction' n with n hn
  · simp only [Nat.zero_eq, pow_zero, powHalf_zero, one_smul]
  · 

Proof state:
case succ
n : ℕ
hn : 2 ^ n • powHalf n = 1
⊢ 2 ^ Nat.succ n • powHalf (Nat.succ n) = 1

Next tactic:
rw [← hn, ← double_powHalf_succ_eq_powHalf n, smul_smul (2 ^ n) 2 (powHalf n.succ), mul_comm,
      pow_succ]
@[simp]
theorem nsmul_pow_two_powHalf' (n k : ℕ) : 2 ^ n • powHalf (n + k) = powHalf k := by
  

Proof state:
n k : ℕ
⊢ 2 ^ n • powHalf (n + k) = powHalf k

Next tactic:
induction' k with k hk
@[simp]
theorem nsmul_pow_two_powHalf' (n k : ℕ) : 2 ^ n • powHalf (n + k) = powHalf k := by
  induction' k with k hk
  · 

Proof state:
case zero
n : ℕ
⊢ 2 ^ n • powHalf (n + Nat.zero) = powHalf Nat.zero

Next tactic:
simp only [add_zero, Surreal.nsmul_pow_two_powHalf, Nat.zero_eq, eq_self_iff_true,
      Surreal.powHalf_zero]
@[simp]
theorem nsmul_pow_two_powHalf' (n k : ℕ) : 2 ^ n • powHalf (n + k) = powHalf k := by
  induction' k with k hk
  · simp only [add_zero, Surreal.nsmul_pow_two_powHalf, Nat.zero_eq, eq_self_iff_true,
      Surreal.powHalf_zero]
  · 

Proof state:
case succ
n k : ℕ
hk : 2 ^ n • powHalf (n + k) = powHalf k
⊢ 2 ^ n • powHalf (n + Nat.succ k) = powHalf (Nat.succ k)

Next tactic:
rw [← double_powHalf_succ_eq_powHalf (n + k), ← double_powHalf_succ_eq_powHalf k,
      smul_algebra_smul_comm] at hk
@[simp]
theorem nsmul_pow_two_powHalf' (n k : ℕ) : 2 ^ n • powHalf (n + k) = powHalf k := by
  induction' k with k hk
  · simp only [add_zero, Surreal.nsmul_pow_two_powHalf, Nat.zero_eq, eq_self_iff_true,
      Surreal.powHalf_zero]
  · rw [← double_powHalf_succ_eq_powHalf (n + k), ← double_powHalf_succ_eq_powHalf k,
      smul_algebra_smul_comm] at hk
    

Proof state:
case succ
n k : ℕ
hk : 2 • 2 ^ n • powHalf (Nat.succ (n + k)) = 2 • powHalf (Nat.succ k)
⊢ 2 ^ n • powHalf (n + Nat.succ k) = powHalf (Nat.succ k)

Next tactic:
rwa [← zsmul_eq_zsmul_iff' two_ne_zero]
theorem zsmul_pow_two_powHalf (m : ℤ) (n k : ℕ) :
    (m * 2 ^ n) • powHalf (n + k) = m • powHalf k := by
  

Proof state:
m : ℤ
n k : ℕ
⊢ (m * 2 ^ n) • powHalf (n + k) = m • powHalf k

Next tactic:
rw [mul_zsmul]
theorem zsmul_pow_two_powHalf (m : ℤ) (n k : ℕ) :
    (m * 2 ^ n) • powHalf (n + k) = m • powHalf k := by
  rw [mul_zsmul]
  

Proof state:
m : ℤ
n k : ℕ
⊢ m • 2 ^ n • powHalf (n + k) = m • powHalf k

Next tactic:
congr
theorem zsmul_pow_two_powHalf (m : ℤ) (n k : ℕ) :
    (m * 2 ^ n) • powHalf (n + k) = m • powHalf k := by
  rw [mul_zsmul]
  congr
  

Proof state:
case e_a
m : ℤ
n k : ℕ
⊢ 2 ^ n • powHalf (n + k) = powHalf k

Next tactic:
norm_cast
theorem zsmul_pow_two_powHalf (m : ℤ) (n k : ℕ) :
    (m * 2 ^ n) • powHalf (n + k) = m • powHalf k := by
  rw [mul_zsmul]
  congr
  norm_cast
  

Proof state:
case e_a
m : ℤ
n k : ℕ
⊢ 2 ^ n • powHalf (n + k) = powHalf k

Next tactic:
exact nsmul_pow_two_powHalf' n k
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  

Proof state:
m₁ m₂ : ℤ
y₁ y₂ : ℕ
h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂
⊢ m₁ • powHalf y₂ = m₂ • powHalf y₁

Next tactic:
revert m₁ m₂
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  

Proof state:
y₁ y₂ : ℕ
⊢ ∀ {m₁ m₂ : ℤ}, m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂ → m₁ • powHalf y₂ = m₂ • powHalf y₁

Next tactic:
wlog h : y₁ ≤ y₂
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · 

Proof state:
case inr
y₁ y₂ : ℕ
this : ∀ {y₁ y₂ : ℕ}, y₁ ≤ y₂ → ∀ {m₁ m₂ : ℤ}, m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂ → m₁ • powHalf y₂ = m₂ • powHalf y₁
h : ¬y₁ ≤ y₂
⊢ ∀ {m₁ m₂ : ℤ}, m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂ → m₁ • powHalf y₂ = m₂ • powHalf y₁

Next tactic:
intro m₁ m₂ aux
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · intro m₁ m₂ aux; 

Proof state:
case inr
y₁ y₂ : ℕ
this : ∀ {y₁ y₂ : ℕ}, y₁ ≤ y₂ → ∀ {m₁ m₂ : ℤ}, m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂ → m₁ • powHalf y₂ = m₂ • powHalf y₁
h : ¬y₁ ≤ y₂
m₁ m₂ : ℤ
aux : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂
⊢ m₁ • powHalf y₂ = m₂ • powHalf y₁

Next tactic:
exact (this (le_of_not_le h) aux.symm).symm
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · intro m₁ m₂ aux; exact (this (le_of_not_le h) aux.symm).symm
  

Proof state:
y₁ y₂ : ℕ
h : y₁ ≤ y₂
⊢ ∀ {m₁ m₂ : ℤ}, m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂ → m₁ • powHalf y₂ = m₂ • powHalf y₁

Next tactic:
intro m₁ m₂ h₂
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · intro m₁ m₂ aux; exact (this (le_of_not_le h) aux.symm).symm
  intro m₁ m₂ h₂
  

Proof state:
y₁ y₂ : ℕ
h : y₁ ≤ y₂
m₁ m₂ : ℤ
h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂
⊢ m₁ • powHalf y₂ = m₂ • powHalf y₁

Next tactic:
obtain ⟨c, rfl⟩ := le_iff_exists_add.mp h
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · intro m₁ m₂ aux; exact (this (le_of_not_le h) aux.symm).symm
  intro m₁ m₂ h₂
  obtain ⟨c, rfl⟩ := le_iff_exists_add.mp h
  

Proof state:
case intro
y₁ : ℕ
m₁ m₂ : ℤ
c : ℕ
h : y₁ ≤ y₁ + c
h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ (y₁ + c)
⊢ m₁ • powHalf (y₁ + c) = m₂ • powHalf y₁

Next tactic:
rw [add_comm, pow_add, ← mul_assoc, mul_eq_mul_right_iff] at h₂
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · intro m₁ m₂ aux; exact (this (le_of_not_le h) aux.symm).symm
  intro m₁ m₂ h₂
  obtain ⟨c, rfl⟩ := le_iff_exists_add.mp h
  rw [add_comm, pow_add, ← mul_assoc, mul_eq_mul_right_iff] at h₂
  

Proof state:
case intro
y₁ : ℕ
m₁ m₂ : ℤ
c : ℕ
h : y₁ ≤ y₁ + c
h₂ : m₁ = m₂ * 2 ^ c ∨ 2 ^ y₁ = 0
⊢ m₁ • powHalf (y₁ + c) = m₂ • powHalf y₁

Next tactic:
cases' h₂ with h₂ h₂
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · intro m₁ m₂ aux; exact (this (le_of_not_le h) aux.symm).symm
  intro m₁ m₂ h₂
  obtain ⟨c, rfl⟩ := le_iff_exists_add.mp h
  rw [add_comm, pow_add, ← mul_assoc, mul_eq_mul_right_iff] at h₂
  cases' h₂ with h₂ h₂
  · 

Proof state:
case intro.inl
y₁ : ℕ
m₁ m₂ : ℤ
c : ℕ
h : y₁ ≤ y₁ + c
h₂ : m₁ = m₂ * 2 ^ c
⊢ m₁ • powHalf (y₁ + c) = m₂ • powHalf y₁

Next tactic:
rw [h₂, add_comm, zsmul_pow_two_powHalf m₂ c y₁]
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · intro m₁ m₂ aux; exact (this (le_of_not_le h) aux.symm).symm
  intro m₁ m₂ h₂
  obtain ⟨c, rfl⟩ := le_iff_exists_add.mp h
  rw [add_comm, pow_add, ← mul_assoc, mul_eq_mul_right_iff] at h₂
  cases' h₂ with h₂ h₂
  · rw [h₂, add_comm, zsmul_pow_two_powHalf m₂ c y₁]
  · 

Proof state:
case intro.inr
y₁ : ℕ
m₁ m₂ : ℤ
c : ℕ
h : y₁ ≤ y₁ + c
h₂ : 2 ^ y₁ = 0
⊢ m₁ • powHalf (y₁ + c) = m₂ • powHalf y₁

Next tactic:
have := Nat.one_le_pow y₁ 2 Nat.succ_pos'
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · intro m₁ m₂ aux; exact (this (le_of_not_le h) aux.symm).symm
  intro m₁ m₂ h₂
  obtain ⟨c, rfl⟩ := le_iff_exists_add.mp h
  rw [add_comm, pow_add, ← mul_assoc, mul_eq_mul_right_iff] at h₂
  cases' h₂ with h₂ h₂
  · rw [h₂, add_comm, zsmul_pow_two_powHalf m₂ c y₁]
  · have := Nat.one_le_pow y₁ 2 Nat.succ_pos'
    

Proof state:
case intro.inr
y₁ : ℕ
m₁ m₂ : ℤ
c : ℕ
h : y₁ ≤ y₁ + c
h₂ : 2 ^ y₁ = 0
this : 1 ≤ 2 ^ y₁
⊢ m₁ • powHalf (y₁ + c) = m₂ • powHalf y₁

Next tactic:
norm_cast at h₂
theorem dyadic_aux {m₁ m₂ : ℤ} {y₁ y₂ : ℕ} (h₂ : m₁ * 2 ^ y₁ = m₂ * 2 ^ y₂) :
    m₁ • powHalf y₂ = m₂ • powHalf y₁ := by
  revert m₁ m₂
  wlog h : y₁ ≤ y₂
  · intro m₁ m₂ aux; exact (this (le_of_not_le h) aux.symm).symm
  intro m₁ m₂ h₂
  obtain ⟨c, rfl⟩ := le_iff_exists_add.mp h
  rw [add_comm, pow_add, ← mul_assoc, mul_eq_mul_right_iff] at h₂
  cases' h₂ with h₂ h₂
  · rw [h₂, add_comm, zsmul_pow_two_powHalf m₂ c y₁]
  · have := Nat.one_le_pow y₁ 2 Nat.succ_pos'
    norm_cast at h₂; 

Proof state:
case intro.inr
y₁ : ℕ
m₁ m₂ : ℤ
c : ℕ
h : y₁ ≤ y₁ + c
this : 1 ≤ 2 ^ y₁
h₂ : 2 ^ y₁ = 0
⊢ m₁ • powHalf (y₁ + c) = m₂ • powHalf y₁

Next tactic:
linarith
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      

Proof state:
x : Localization.Away 2
⊢ ∀ {a c : ℤ} {b d : ↥(Submonoid.powers 2)},
    (Localization.r (Submonoid.powers 2)) (a, b) (c, d) → a • powHalf (Submonoid.log b) = c • powHalf (Submonoid.log d)

Next tactic:
intro m₁ m₂ n₁ n₂ h₁
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      

Proof state:
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      

Proof state:
case intro.mk.intro
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h₂ :
  ↑{ val := n₃, property := (_ : ∃ y, (fun x => 2 ^ x) y = n₃) } * (↑(m₂, n₂).2 * (m₁, n₁).1) =
    ↑{ val := n₃, property := (_ : ∃ y, (fun x => 2 ^ x) y = n₃) } * (↑(m₁, n₁).2 * (m₂, n₂).1)
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      

Proof state:
case intro.mk.intro
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h₂ : ↑n₂ * m₁ = ↑n₁ * m₂ ∨ n₃ = 0
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
cases h₂
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · 

Proof state:
case intro.mk.intro.inl
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : ↑n₂ * m₁ = ↑n₁ * m₂
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
obtain ⟨a₁, ha₁⟩ := n₁.prop
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · obtain ⟨a₁, ha₁⟩ := n₁.prop
        

Proof state:
case intro.mk.intro.inl.intro
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : ↑n₂ * m₁ = ↑n₁ * m₂
a₁ : ℕ
ha₁ : (fun x => 2 ^ x) a₁ = ↑n₁
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
obtain ⟨a₂, ha₂⟩ := n₂.prop
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · obtain ⟨a₁, ha₁⟩ := n₁.prop
        obtain ⟨a₂, ha₂⟩ := n₂.prop
        

Proof state:
case intro.mk.intro.inl.intro.intro
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : ↑n₂ * m₁ = ↑n₁ * m₂
a₁ : ℕ
ha₁ : (fun x => 2 ^ x) a₁ = ↑n₁
a₂ : ℕ
ha₂ : (fun x => 2 ^ x) a₂ = ↑n₂
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
simp only at ha₁ ha₂ ⊢
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · obtain ⟨a₁, ha₁⟩ := n₁.prop
        obtain ⟨a₂, ha₂⟩ := n₂.prop
        simp only at ha₁ ha₂ ⊢
        

Proof state:
case intro.mk.intro.inl.intro.intro
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : ↑n₂ * m₁ = ↑n₁ * m₂
a₁ : ℕ
ha₁ : 2 ^ a₁ = ↑n₁
a₂ : ℕ
ha₂ : 2 ^ a₂ = ↑n₂
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
have hn₁ : n₁ = Submonoid.pow 2 a₁ := Subtype.ext ha₁.symm
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · obtain ⟨a₁, ha₁⟩ := n₁.prop
        obtain ⟨a₂, ha₂⟩ := n₂.prop
        simp only at ha₁ ha₂ ⊢
        have hn₁ : n₁ = Submonoid.pow 2 a₁ := Subtype.ext ha₁.symm
        

Proof state:
case intro.mk.intro.inl.intro.intro
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : ↑n₂ * m₁ = ↑n₁ * m₂
a₁ : ℕ
ha₁ : 2 ^ a₁ = ↑n₁
a₂ : ℕ
ha₂ : 2 ^ a₂ = ↑n₂
hn₁ : n₁ = Submonoid.pow 2 a₁
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
have hn₂ : n₂ = Submonoid.pow 2 a₂ := Subtype.ext ha₂.symm
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · obtain ⟨a₁, ha₁⟩ := n₁.prop
        obtain ⟨a₂, ha₂⟩ := n₂.prop
        simp only at ha₁ ha₂ ⊢
        have hn₁ : n₁ = Submonoid.pow 2 a₁ := Subtype.ext ha₁.symm
        have hn₂ : n₂ = Submonoid.pow 2 a₂ := Subtype.ext ha₂.symm
        

Proof state:
case intro.mk.intro.inl.intro.intro
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : ↑n₂ * m₁ = ↑n₁ * m₂
a₁ : ℕ
ha₁ : 2 ^ a₁ = ↑n₁
a₂ : ℕ
ha₂ : 2 ^ a₂ = ↑n₂
hn₁ : n₁ = Submonoid.pow 2 a₁
hn₂ : n₂ = Submonoid.pow 2 a₂
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
have h₂ : 1 < (2 : ℤ).natAbs := one_lt_two
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · obtain ⟨a₁, ha₁⟩ := n₁.prop
        obtain ⟨a₂, ha₂⟩ := n₂.prop
        simp only at ha₁ ha₂ ⊢
        have hn₁ : n₁ = Submonoid.pow 2 a₁ := Subtype.ext ha₁.symm
        have hn₂ : n₂ = Submonoid.pow 2 a₂ := Subtype.ext ha₂.symm
        have h₂ : 1 < (2 : ℤ).natAbs := one_lt_two
        

Proof state:
case intro.mk.intro.inl.intro.intro
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : ↑n₂ * m₁ = ↑n₁ * m₂
a₁ : ℕ
ha₁ : 2 ^ a₁ = ↑n₁
a₂ : ℕ
ha₂ : 2 ^ a₂ = ↑n₂
hn₁ : n₁ = Submonoid.pow 2 a₁
hn₂ : n₂ = Submonoid.pow 2 a₂
h₂ : 1 < Int.natAbs 2
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
rw [hn₁, hn₂, Submonoid.log_pow_int_eq_self h₂, Submonoid.log_pow_int_eq_self h₂]
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · obtain ⟨a₁, ha₁⟩ := n₁.prop
        obtain ⟨a₂, ha₂⟩ := n₂.prop
        simp only at ha₁ ha₂ ⊢
        have hn₁ : n₁ = Submonoid.pow 2 a₁ := Subtype.ext ha₁.symm
        have hn₂ : n₂ = Submonoid.pow 2 a₂ := Subtype.ext ha₂.symm
        have h₂ : 1 < (2 : ℤ).natAbs := one_lt_two
        rw [hn₁, hn₂, Submonoid.log_pow_int_eq_self h₂, Submonoid.log_pow_int_eq_self h₂]
        

Proof state:
case intro.mk.intro.inl.intro.intro
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : ↑n₂ * m₁ = ↑n₁ * m₂
a₁ : ℕ
ha₁ : 2 ^ a₁ = ↑n₁
a₂ : ℕ
ha₂ : 2 ^ a₂ = ↑n₂
hn₁ : n₁ = Submonoid.pow 2 a₁
hn₂ : n₂ = Submonoid.pow 2 a₂
h₂ : 1 < Int.natAbs 2
⊢ m₁ • powHalf a₁ = m₂ • powHalf a₂

Next tactic:
apply dyadic_aux
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · obtain ⟨a₁, ha₁⟩ := n₁.prop
        obtain ⟨a₂, ha₂⟩ := n₂.prop
        simp only at ha₁ ha₂ ⊢
        have hn₁ : n₁ = Submonoid.pow 2 a₁ := Subtype.ext ha₁.symm
        have hn₂ : n₂ = Submonoid.pow 2 a₂ := Subtype.ext ha₂.symm
        have h₂ : 1 < (2 : ℤ).natAbs := one_lt_two
        rw [hn₁, hn₂, Submonoid.log_pow_int_eq_self h₂, Submonoid.log_pow_int_eq_self h₂]
        apply dyadic_aux
        

Proof state:
case intro.mk.intro.inl.intro.intro.h₂
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : ↑n₂ * m₁ = ↑n₁ * m₂
a₁ : ℕ
ha₁ : 2 ^ a₁ = ↑n₁
a₂ : ℕ
ha₂ : 2 ^ a₂ = ↑n₂
hn₁ : n₁ = Submonoid.pow 2 a₁
hn₂ : n₂ = Submonoid.pow 2 a₂
h₂ : 1 < Int.natAbs 2
⊢ m₁ * 2 ^ a₂ = m₂ * 2 ^ a₁

Next tactic:
rwa [ha₁, ha₂, mul_comm, mul_comm m₂]
/-- The additive monoid morphism `dyadicMap` sends ⟦⟨m, 2^n⟩⟧ to m • half ^ n. -/
def dyadicMap : Localization.Away (2 : ℤ) →+ Surreal where
  toFun x :=
    (Localization.liftOn x fun x y => x • powHalf (Submonoid.log y)) <| by
      intro m₁ m₂ n₁ n₂ h₁
      obtain ⟨⟨n₃, y₃, hn₃⟩, h₂⟩ := Localization.r_iff_exists.mp h₁
      simp only [Subtype.coe_mk, mul_eq_mul_left_iff] at h₂
      cases h₂
      · obtain ⟨a₁, ha₁⟩ := n₁.prop
        obtain ⟨a₂, ha₂⟩ := n₂.prop
        simp only at ha₁ ha₂ ⊢
        have hn₁ : n₁ = Submonoid.pow 2 a₁ := Subtype.ext ha₁.symm
        have hn₂ : n₂ = Submonoid.pow 2 a₂ := Subtype.ext ha₂.symm
        have h₂ : 1 < (2 : ℤ).natAbs := one_lt_two
        rw [hn₁, hn₂, Submonoid.log_pow_int_eq_self h₂, Submonoid.log_pow_int_eq_self h₂]
        apply dyadic_aux
        rwa [ha₁, ha₂, mul_comm, mul_comm m₂]
      · 

Proof state:
case intro.mk.intro.inr
x : Localization.Away 2
m₁ m₂ : ℤ
n₁ n₂ : ↥(Submonoid.powers 2)
h₁ : (Localization.r (Submonoid.powers 2)) (m₁, n₁) (m₂, n₂)
n₃ : ℤ
y₃ : ℕ
hn₃ : (fun x => 2 ^ x) y₃ = n₃
h✝ : n₃ = 0
⊢ m₁ • powHalf (Submonoid.log n₁) = m₂ • powHalf (Submonoid.log n₂)

Next tactic:
have : (1 : ℤ) ≤ 2 ^ y₃ := mod_cast Nat.one_le_pow y₃ 2 Nat.succ_pos'