l3lab/ntp-mathlib huggingface dataset:
/-- A ring homomorphism between local rings is a local ring hom iff it reflects units,
i.e. any preimage of a unit is still a unit. https://stacks.math.columbia.edu/tag/07BJ
-/
theorem local_hom_TFAE (f : R →+* S) :
    List.TFAE
      [IsLocalRingHom f, f '' (maximalIdeal R).1 ⊆ maximalIdeal S,
        (maximalIdeal R).map f ≤ maximalIdeal S, maximalIdeal R ≤ (maximalIdeal S).comap f,
        (maximalIdeal S).comap f = maximalIdeal R] := by
  tfae_have 1 → 2
  · rintro _ _ ⟨a, ha, rfl⟩
    exact map_nonunit f a ha
  tfae_have 2 → 4
  · exact Set.image_subset_iff.1
  tfae_have 3 ↔ 4
  · exact Ideal.map_le_iff_le_comap
  tfae_have 4 → 1
  · intro h
    constructor
    exact fun x => not_imp_not.1 (@h x)
  tfae_have 1 → 5
  · intro
    ext
    exact not_iff_not.2 (isUnit_map_iff f _)
  tfae_have 5 → 4
  · 

Proof state:
case tfae_5_to_4
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝³ : CommSemiring R
inst✝² : LocalRing R
inst✝¹ : CommSemiring S
inst✝ : LocalRing S
f : R →+* S
tfae_1_to_2 : IsLocalRingHom f → ⇑f '' ↑(maximalIdeal R).toAddSubmonoid ⊆ ↑(maximalIdeal S)
tfae_2_to_4 :
  ⇑f '' ↑(maximalIdeal R).toAddSubmonoid ⊆ ↑(maximalIdeal S) → maximalIdeal R ≤ Ideal.comap f (maximalIdeal S)
tfae_3_iff_4 : Ideal.map f (maximalIdeal R) ≤ maximalIdeal S ↔ maximalIdeal R ≤ Ideal.comap f (maximalIdeal S)
tfae_4_to_1 : maximalIdeal R ≤ Ideal.comap f (maximalIdeal S) → IsLocalRingHom f
tfae_1_to_5 : IsLocalRingHom f → Ideal.comap f (maximalIdeal S) = maximalIdeal R
⊢ Ideal.comap f (maximalIdeal S) = maximalIdeal R → maximalIdeal R ≤ Ideal.comap f (maximalIdeal S)

Next tactic:
exact fun h => le_of_eq h.symm
/-- A ring homomorphism between local rings is a local ring hom iff it reflects units,
i.e. any preimage of a unit is still a unit. https://stacks.math.columbia.edu/tag/07BJ
-/
theorem local_hom_TFAE (f : R →+* S) :
    List.TFAE
      [IsLocalRingHom f, f '' (maximalIdeal R).1 ⊆ maximalIdeal S,
        (maximalIdeal R).map f ≤ maximalIdeal S, maximalIdeal R ≤ (maximalIdeal S).comap f,
        (maximalIdeal S).comap f = maximalIdeal R] := by
  tfae_have 1 → 2
  · rintro _ _ ⟨a, ha, rfl⟩
    exact map_nonunit f a ha
  tfae_have 2 → 4
  · exact Set.image_subset_iff.1
  tfae_have 3 ↔ 4
  · exact Ideal.map_le_iff_le_comap
  tfae_have 4 → 1
  · intro h
    constructor
    exact fun x => not_imp_not.1 (@h x)
  tfae_have 1 → 5
  · intro
    ext
    exact not_iff_not.2 (isUnit_map_iff f _)
  tfae_have 5 → 4
  · exact fun h => le_of_eq h.symm
  

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝³ : CommSemiring R
inst✝² : LocalRing R
inst✝¹ : CommSemiring S
inst✝ : LocalRing S
f : R →+* S
tfae_1_to_2 : IsLocalRingHom f → ⇑f '' ↑(maximalIdeal R).toAddSubmonoid ⊆ ↑(maximalIdeal S)
tfae_2_to_4 :
  ⇑f '' ↑(maximalIdeal R).toAddSubmonoid ⊆ ↑(maximalIdeal S) → maximalIdeal R ≤ Ideal.comap f (maximalIdeal S)
tfae_3_iff_4 : Ideal.map f (maximalIdeal R) ≤ maximalIdeal S ↔ maximalIdeal R ≤ Ideal.comap f (maximalIdeal S)
tfae_4_to_1 : maximalIdeal R ≤ Ideal.comap f (maximalIdeal S) → IsLocalRingHom f
tfae_1_to_5 : IsLocalRingHom f → Ideal.comap f (maximalIdeal S) = maximalIdeal R
tfae_5_to_4 : Ideal.comap f (maximalIdeal S) = maximalIdeal R → maximalIdeal R ≤ Ideal.comap f (maximalIdeal S)
⊢ List.TFAE
    [IsLocalRingHom f, ⇑f '' ↑(maximalIdeal R).toAddSubmonoid ⊆ ↑(maximalIdeal S),
      Ideal.map f (maximalIdeal R) ≤ maximalIdeal S, maximalIdeal R ≤ Ideal.comap f (maximalIdeal S),
      Ideal.comap f (maximalIdeal S) = maximalIdeal R]

Next tactic:
tfae_finish
theorem of_surjective [CommSemiring R] [LocalRing R] [CommSemiring S] [Nontrivial S] (f : R →+* S)
    [IsLocalRingHom f] (hf : Function.Surjective f) : LocalRing S :=
  of_isUnit_or_isUnit_of_isUnit_add (by
    

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁴ : CommSemiring R
inst✝³ : LocalRing R
inst✝² : CommSemiring S
inst✝¹ : Nontrivial S
f : R →+* S
inst✝ : IsLocalRingHom f
hf : Function.Surjective ⇑f
⊢ ∀ (a b : S), IsUnit (a + b) → IsUnit a ∨ IsUnit b

Next tactic:
intro a b hab
theorem of_surjective [CommSemiring R] [LocalRing R] [CommSemiring S] [Nontrivial S] (f : R →+* S)
    [IsLocalRingHom f] (hf : Function.Surjective f) : LocalRing S :=
  of_isUnit_or_isUnit_of_isUnit_add (by
    intro a b hab
    

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁴ : CommSemiring R
inst✝³ : LocalRing R
inst✝² : CommSemiring S
inst✝¹ : Nontrivial S
f : R →+* S
inst✝ : IsLocalRingHom f
hf : Function.Surjective ⇑f
a b : S
hab : IsUnit (a + b)
⊢ IsUnit a ∨ IsUnit b

Next tactic:
obtain ⟨a, rfl⟩ := hf a
theorem of_surjective [CommSemiring R] [LocalRing R] [CommSemiring S] [Nontrivial S] (f : R →+* S)
    [IsLocalRingHom f] (hf : Function.Surjective f) : LocalRing S :=
  of_isUnit_or_isUnit_of_isUnit_add (by
    intro a b hab
    obtain ⟨a, rfl⟩ := hf a
    

Proof state:
case intro
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁴ : CommSemiring R
inst✝³ : LocalRing R
inst✝² : CommSemiring S
inst✝¹ : Nontrivial S
f : R →+* S
inst✝ : IsLocalRingHom f
hf : Function.Surjective ⇑f
b : S
a : R
hab : IsUnit (f a + b)
⊢ IsUnit (f a) ∨ IsUnit b

Next tactic:
obtain ⟨b, rfl⟩ := hf b
theorem of_surjective [CommSemiring R] [LocalRing R] [CommSemiring S] [Nontrivial S] (f : R →+* S)
    [IsLocalRingHom f] (hf : Function.Surjective f) : LocalRing S :=
  of_isUnit_or_isUnit_of_isUnit_add (by
    intro a b hab
    obtain ⟨a, rfl⟩ := hf a
    obtain ⟨b, rfl⟩ := hf b
    

Proof state:
case intro.intro
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁴ : CommSemiring R
inst✝³ : LocalRing R
inst✝² : CommSemiring S
inst✝¹ : Nontrivial S
f : R →+* S
inst✝ : IsLocalRingHom f
hf : Function.Surjective ⇑f
a b : R
hab : IsUnit (f a + f b)
⊢ IsUnit (f a) ∨ IsUnit (f b)

Next tactic:
rw [← map_add] at hab
theorem of_surjective [CommSemiring R] [LocalRing R] [CommSemiring S] [Nontrivial S] (f : R →+* S)
    [IsLocalRingHom f] (hf : Function.Surjective f) : LocalRing S :=
  of_isUnit_or_isUnit_of_isUnit_add (by
    intro a b hab
    obtain ⟨a, rfl⟩ := hf a
    obtain ⟨b, rfl⟩ := hf b
    rw [← map_add] at hab
    

Proof state:
case intro.intro
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁴ : CommSemiring R
inst✝³ : LocalRing R
inst✝² : CommSemiring S
inst✝¹ : Nontrivial S
f : R →+* S
inst✝ : IsLocalRingHom f
hf : Function.Surjective ⇑f
a b : R
hab : IsUnit (f (a + b))
⊢ IsUnit (f a) ∨ IsUnit (f b)

Next tactic:
exact
      (isUnit_or_isUnit_of_isUnit_add <| IsLocalRingHom.map_nonunit _ hab).imp f.isUnit_map
        f.isUnit_map
/-- If `f : R →+* S` is a surjective local ring hom, then the induced units map is surjective. -/
theorem surjective_units_map_of_local_ringHom [CommRing R] [CommRing S] (f : R →+* S)
    (hf : Function.Surjective f) (h : IsLocalRingHom f) :
    Function.Surjective (Units.map <| f.toMonoidHom) := by
  

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝¹ : CommRing R
inst✝ : CommRing S
f : R →+* S
hf : Function.Surjective ⇑f
h : IsLocalRingHom f
⊢ Function.Surjective ⇑(Units.map ↑f)

Next tactic:
intro a
/-- If `f : R →+* S` is a surjective local ring hom, then the induced units map is surjective. -/
theorem surjective_units_map_of_local_ringHom [CommRing R] [CommRing S] (f : R →+* S)
    (hf : Function.Surjective f) (h : IsLocalRingHom f) :
    Function.Surjective (Units.map <| f.toMonoidHom) := by
  intro a
  

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝¹ : CommRing R
inst✝ : CommRing S
f : R →+* S
hf : Function.Surjective ⇑f
h : IsLocalRingHom f
a : Sˣ
⊢ ∃ a_1, (Units.map ↑f) a_1 = a

Next tactic:
obtain ⟨b, hb⟩ := hf (a : S)
/-- If `f : R →+* S` is a surjective local ring hom, then the induced units map is surjective. -/
theorem surjective_units_map_of_local_ringHom [CommRing R] [CommRing S] (f : R →+* S)
    (hf : Function.Surjective f) (h : IsLocalRingHom f) :
    Function.Surjective (Units.map <| f.toMonoidHom) := by
  intro a
  obtain ⟨b, hb⟩ := hf (a : S)
  

Proof state:
case intro
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝¹ : CommRing R
inst✝ : CommRing S
f : R →+* S
hf : Function.Surjective ⇑f
h : IsLocalRingHom f
a : Sˣ
b : R
hb : f b = ↑a
⊢ ∃ a_1, (Units.map ↑f) a_1 = a

Next tactic:
use (isUnit_of_map_unit f b (by rw [hb]; exact Units.isUnit _)).unit
/-- If `f : R →+* S` is a surjective local ring hom, then the induced units map is surjective. -/
theorem surjective_units_map_of_local_ringHom [CommRing R] [CommRing S] (f : R →+* S)
    (hf : Function.Surjective f) (h : IsLocalRingHom f) :
    Function.Surjective (Units.map <| f.toMonoidHom) := by
  intro a
  obtain ⟨b, hb⟩ := hf (a : S)
  use (isUnit_of_map_unit f b (by 

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝¹ : CommRing R
inst✝ : CommRing S
f : R →+* S
hf : Function.Surjective ⇑f
h : IsLocalRingHom f
a : Sˣ
b : R
hb : f b = ↑a
⊢ IsUnit (f b)

Next tactic:
rw [hb]
/-- If `f : R →+* S` is a surjective local ring hom, then the induced units map is surjective. -/
theorem surjective_units_map_of_local_ringHom [CommRing R] [CommRing S] (f : R →+* S)
    (hf : Function.Surjective f) (h : IsLocalRingHom f) :
    Function.Surjective (Units.map <| f.toMonoidHom) := by
  intro a
  obtain ⟨b, hb⟩ := hf (a : S)
  use (isUnit_of_map_unit f b (by rw [hb]; 

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝¹ : CommRing R
inst✝ : CommRing S
f : R →+* S
hf : Function.Surjective ⇑f
h : IsLocalRingHom f
a : Sˣ
b : R
hb : f b = ↑a
⊢ IsUnit ↑a

Next tactic:
exact Units.isUnit _
/-- If `f : R →+* S` is a surjective local ring hom, then the induced units map is surjective. -/
theorem surjective_units_map_of_local_ringHom [CommRing R] [CommRing S] (f : R →+* S)
    (hf : Function.Surjective f) (h : IsLocalRingHom f) :
    Function.Surjective (Units.map <| f.toMonoidHom) := by
  intro a
  obtain ⟨b, hb⟩ := hf (a : S)
  use (isUnit_of_map_unit f b (by rw [hb]; exact Units.isUnit _)).unit
  

Proof state:
case h
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝¹ : CommRing R
inst✝ : CommRing S
f : R →+* S
hf : Function.Surjective ⇑f
h : IsLocalRingHom f
a : Sˣ
b : R
hb : f b = ↑a
⊢ (Units.map ↑f) (IsUnit.unit (_ : IsUnit b)) = a

Next tactic:
ext
/-- If `f : R →+* S` is a surjective local ring hom, then the induced units map is surjective. -/
theorem surjective_units_map_of_local_ringHom [CommRing R] [CommRing S] (f : R →+* S)
    (hf : Function.Surjective f) (h : IsLocalRingHom f) :
    Function.Surjective (Units.map <| f.toMonoidHom) := by
  intro a
  obtain ⟨b, hb⟩ := hf (a : S)
  use (isUnit_of_map_unit f b (by rw [hb]; exact Units.isUnit _)).unit
  ext
  

Proof state:
case h.a
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝¹ : CommRing R
inst✝ : CommRing S
f : R →+* S
hf : Function.Surjective ⇑f
h : IsLocalRingHom f
a : Sˣ
b : R
hb : f b = ↑a
⊢ ↑((Units.map ↑f) (IsUnit.unit (_ : IsUnit b))) = ↑a

Next tactic:
exact hb
/-- The map on residue fields induced by a local homomorphism between local rings -/
def map (f : R →+* S) [IsLocalRingHom f] : ResidueField R →+* ResidueField S :=
  Ideal.Quotient.lift (maximalIdeal R) ((Ideal.Quotient.mk _).comp f) fun a ha => by
    

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁶ : CommRing R
inst✝⁵ : LocalRing R
inst✝⁴ : CommRing S
inst✝³ : LocalRing S
inst✝² : CommRing T
inst✝¹ : LocalRing T
f : R →+* S
inst✝ : IsLocalRingHom f
a : R
ha : a ∈ maximalIdeal R
⊢ (RingHom.comp (Ideal.Quotient.mk (maximalIdeal S)) f) a = 0

Next tactic:
erw [Ideal.Quotient.eq_zero_iff_mem]
/-- The map on residue fields induced by a local homomorphism between local rings -/
def map (f : R →+* S) [IsLocalRingHom f] : ResidueField R →+* ResidueField S :=
  Ideal.Quotient.lift (maximalIdeal R) ((Ideal.Quotient.mk _).comp f) fun a ha => by
    erw [Ideal.Quotient.eq_zero_iff_mem]
    

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁶ : CommRing R
inst✝⁵ : LocalRing R
inst✝⁴ : CommRing S
inst✝³ : LocalRing S
inst✝² : CommRing T
inst✝¹ : LocalRing T
f : R →+* S
inst✝ : IsLocalRingHom f
a : R
ha : a ∈ maximalIdeal R
⊢ f a ∈ maximalIdeal S

Next tactic:
exact map_nonunit f a ha
/-- A ring isomorphism defines an isomorphism of residue fields. -/
@[simps apply]
def mapEquiv (f : R ≃+* S) : LocalRing.ResidueField R ≃+* LocalRing.ResidueField S where
  toFun := map (f : R →+* S)
  invFun := map (f.symm : S →+* R)
  left_inv x := by 

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁵ : CommRing R
inst✝⁴ : LocalRing R
inst✝³ : CommRing S
inst✝² : LocalRing S
inst✝¹ : CommRing T
inst✝ : LocalRing T
f : R ≃+* S
x : ResidueField R
⊢ (map ↑(RingEquiv.symm f)) ((map ↑f) x) = x

Next tactic:
simp only [map_map, RingEquiv.symm_comp, map_id, RingHom.id_apply]
/-- A ring isomorphism defines an isomorphism of residue fields. -/
@[simps apply]
def mapEquiv (f : R ≃+* S) : LocalRing.ResidueField R ≃+* LocalRing.ResidueField S where
  toFun := map (f : R →+* S)
  invFun := map (f.symm : S →+* R)
  left_inv x := by simp only [map_map, RingEquiv.symm_comp, map_id, RingHom.id_apply]
  right_inv x := by 

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁵ : CommRing R
inst✝⁴ : LocalRing R
inst✝³ : CommRing S
inst✝² : LocalRing S
inst✝¹ : CommRing T
inst✝ : LocalRing T
f : R ≃+* S
x : ResidueField S
⊢ (map ↑f) ((map ↑(RingEquiv.symm f)) x) = x

Next tactic:
simp only [map_map, RingEquiv.comp_symm, map_id, RingHom.id_apply]
theorem isLocalRingHom_residue : IsLocalRingHom (LocalRing.residue R) := by
  

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁵ : CommRing R
inst✝⁴ : LocalRing R
inst✝³ : CommRing S
inst✝² : LocalRing S
inst✝¹ : CommRing T
inst✝ : LocalRing T
⊢ IsLocalRingHom (residue R)

Next tactic:
constructor
theorem isLocalRingHom_residue : IsLocalRingHom (LocalRing.residue R) := by
  constructor
  

Proof state:
case map_nonunit
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁵ : CommRing R
inst✝⁴ : LocalRing R
inst✝³ : CommRing S
inst✝² : LocalRing S
inst✝¹ : CommRing T
inst✝ : LocalRing T
⊢ ∀ (a : R), IsUnit ((residue R) a) → IsUnit a

Next tactic:
intro a ha
theorem isLocalRingHom_residue : IsLocalRingHom (LocalRing.residue R) := by
  constructor
  intro a ha
  

Proof state:
case map_nonunit
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁵ : CommRing R
inst✝⁴ : LocalRing R
inst✝³ : CommRing S
inst✝² : LocalRing S
inst✝¹ : CommRing T
inst✝ : LocalRing T
a : R
ha : IsUnit ((residue R) a)
⊢ IsUnit a

Next tactic:
by_contra h
theorem isLocalRingHom_residue : IsLocalRingHom (LocalRing.residue R) := by
  constructor
  intro a ha
  by_contra h
  

Proof state:
case map_nonunit
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁵ : CommRing R
inst✝⁴ : LocalRing R
inst✝³ : CommRing S
inst✝² : LocalRing S
inst✝¹ : CommRing T
inst✝ : LocalRing T
a : R
ha : IsUnit ((residue R) a)
h : ¬IsUnit a
⊢ False

Next tactic:
erw [Ideal.Quotient.eq_zero_iff_mem.mpr ((LocalRing.mem_maximalIdeal _).mpr h)] at ha
theorem isLocalRingHom_residue : IsLocalRingHom (LocalRing.residue R) := by
  constructor
  intro a ha
  by_contra h
  erw [Ideal.Quotient.eq_zero_iff_mem.mpr ((LocalRing.mem_maximalIdeal _).mpr h)] at ha
  

Proof state:
case map_nonunit
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝⁵ : CommRing R
inst✝⁴ : LocalRing R
inst✝³ : CommRing S
inst✝² : LocalRing S
inst✝¹ : CommRing T
inst✝ : LocalRing T
a : R
ha : IsUnit 0
h : ¬IsUnit a
⊢ False

Next tactic:
exact ha.ne_zero rfl
instance (priority := 100) : LocalRing K :=
  LocalRing.of_isUnit_or_isUnit_one_sub_self fun a =>
    if h : a = 0 then Or.inr (by 

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝ : Field K
a : K
h : a = 0
⊢ IsUnit (1 - a)

Next tactic:
rw [h, sub_zero]
instance (priority := 100) : LocalRing K :=
  LocalRing.of_isUnit_or_isUnit_one_sub_self fun a =>
    if h : a = 0 then Or.inr (by rw [h, sub_zero]; 

Proof state:
R : Type u
S : Type v
T : Type w
K : Type u'
inst✝ : Field K
a : K
h : a = 0
⊢ IsUnit 1

Next tactic:
exact isUnit_one
theorem surjective_stableUnderComposition : StableUnderComposition surjective := by
  

Proof state:
⊢ StableUnderComposition fun {X Y} [CommRing X] [CommRing Y] f => Function.Surjective ⇑f

Next tactic:
introv R hf hg
theorem surjective_stableUnderComposition : StableUnderComposition surjective := by
  introv R hf hg; 

Proof state:
R S T : Type u_1
inst✝² : CommRing R
inst✝¹ : CommRing S
inst✝ : CommRing T
f : R →+* S
g : S →+* T
hf : Function.Surjective ⇑f
hg : Function.Surjective ⇑g
⊢ Function.Surjective ⇑(comp g f)

Next tactic:
exact hg.comp hf
theorem surjective_respectsIso : RespectsIso surjective := by
  

Proof state:
⊢ RespectsIso fun {X Y} [CommRing X] [CommRing Y] f => Function.Surjective ⇑f

Next tactic:
apply surjective_stableUnderComposition.respectsIso
theorem surjective_respectsIso : RespectsIso surjective := by
  apply surjective_stableUnderComposition.respectsIso
  

Proof state:
⊢ ∀ {R S : Type u_1} [inst : CommRing R] [inst_1 : CommRing S] (e : R ≃+* S),
    Function.Surjective ⇑(RingEquiv.toRingHom e)

Next tactic:
intros _ _ _ _ e
theorem surjective_respectsIso : RespectsIso surjective := by
  apply surjective_stableUnderComposition.respectsIso
  intros _ _ _ _ e
  

Proof state:
R✝ S✝ : Type u_1
inst✝¹ : CommRing R✝
inst✝ : CommRing S✝
e : R✝ ≃+* S✝
⊢ Function.Surjective ⇑(RingEquiv.toRingHom e)

Next tactic:
exact e.surjective
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  

Proof state:
⊢ StableUnderBaseChange fun {X Y} [CommRing X] [CommRing Y] f => Function.Surjective ⇑f

Next tactic:
refine' StableUnderBaseChange.mk _ surjective_respectsIso _
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  

Proof state:
⊢ ∀ ⦃R S T : Type u_1⦄ [inst : CommRing R] [inst_1 : CommRing S] [inst_2 : CommRing T] [inst_3 : Algebra R S]
    [inst_4 : Algebra R T], Function.Surjective ⇑(algebraMap R T) → Function.Surjective ⇑includeLeftRingHom

Next tactic:
classical
  introv h x
  skip
  induction x using TensorProduct.induction_on with
  | zero => exact ⟨0, map_zero _⟩
  | tmul x y =>
    obtain ⟨y, rfl⟩ := h y; use y • x; dsimp
    rw [TensorProduct.smul_tmul, Algebra.algebraMap_eq_smul_one]
  | add x y ex ey => obtain ⟨⟨x, rfl⟩, ⟨y, rfl⟩⟩ := ex, ey; exact ⟨x + y, map_add _ x y⟩
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  

Proof state:
⊢ ∀ ⦃R S T : Type u_1⦄ [inst : CommRing R] [inst_1 : CommRing S] [inst_2 : CommRing T] [inst_3 : Algebra R S]
    [inst_4 : Algebra R T], Function.Surjective ⇑(algebraMap R T) → Function.Surjective ⇑includeLeftRingHom

Next tactic:
introv h x
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  introv h x
  

Proof state:
R S T : Type u_1
inst✝⁴ : CommRing R
inst✝³ : CommRing S
inst✝² : CommRing T
inst✝¹ : Algebra R S
inst✝ : Algebra R T
h : Function.Surjective ⇑(algebraMap R T)
x : S ⊗[R] T
⊢ ∃ a, includeLeftRingHom a = x

Next tactic:
skip
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  introv h x
  skip
  

Proof state:
R S T : Type u_1
inst✝⁴ : CommRing R
inst✝³ : CommRing S
inst✝² : CommRing T
inst✝¹ : Algebra R S
inst✝ : Algebra R T
h : Function.Surjective ⇑(algebraMap R T)
x : S ⊗[R] T
⊢ ∃ a, includeLeftRingHom a = x

Next tactic:
induction x using TensorProduct.induction_on with
  | zero => exact ⟨0, map_zero _⟩
  | tmul x y =>
    obtain ⟨y, rfl⟩ := h y; use y • x; dsimp
    rw [TensorProduct.smul_tmul, Algebra.algebraMap_eq_smul_one]
  | add x y ex ey => obtain ⟨⟨x, rfl⟩, ⟨y, rfl⟩⟩ := ex, ey; exact ⟨x + y, map_add _ x y⟩
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  introv h x
  skip
  induction x using TensorProduct.induction_on with
  

Proof state:
case zero
R S T : Type u_1
inst✝⁴ : CommRing R
inst✝³ : CommRing S
inst✝² : CommRing T
inst✝¹ : Algebra R S
inst✝ : Algebra R T
h : Function.Surjective ⇑(algebraMap R T)
⊢ ∃ a, includeLeftRingHom a = 0

Next tactic:
| zero => exact ⟨0, map_zero _⟩
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  introv h x
  skip
  induction x using TensorProduct.induction_on with
  | zero => 

Proof state:
case zero
R S T : Type u_1
inst✝⁴ : CommRing R
inst✝³ : CommRing S
inst✝² : CommRing T
inst✝¹ : Algebra R S
inst✝ : Algebra R T
h : Function.Surjective ⇑(algebraMap R T)
⊢ ∃ a, includeLeftRingHom a = 0

Next tactic:
exact ⟨0, map_zero _⟩
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  introv h x
  skip
  induction x using TensorProduct.induction_on with
  | zero => exact ⟨0, map_zero _⟩
  

Proof state:
case tmul
R S T : Type u_1
inst✝⁴ : CommRing R
inst✝³ : CommRing S
inst✝² : CommRing T
inst✝¹ : Algebra R S
inst✝ : Algebra R T
h : Function.Surjective ⇑(algebraMap R T)
x : S
y : T
⊢ ∃ a, includeLeftRingHom a = x ⊗ₜ[R] y

Next tactic:
| tmul x y =>
    obtain ⟨y, rfl⟩ := h y; use y • x; dsimp
    rw [TensorProduct.smul_tmul, Algebra.algebraMap_eq_smul_one]
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  introv h x
  skip
  induction x using TensorProduct.induction_on with
  | zero => exact ⟨0, map_zero _⟩
  | tmul x y =>
    

Proof state:
case tmul
R S T : Type u_1
inst✝⁴ : CommRing R
inst✝³ : CommRing S
inst✝² : CommRing T
inst✝¹ : Algebra R S
inst✝ : Algebra R T
h : Function.Surjective ⇑(algebraMap R T)
x : S
y : T
⊢ ∃ a, includeLeftRingHom a = x ⊗ₜ[R] y

Next tactic:
obtain ⟨y, rfl⟩ := h y
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  introv h x
  skip
  induction x using TensorProduct.induction_on with
  | zero => exact ⟨0, map_zero _⟩
  | tmul x y =>
    obtain ⟨y, rfl⟩ := h y; 

Proof state:
case tmul.intro
R S T : Type u_1
inst✝⁴ : CommRing R
inst✝³ : CommRing S
inst✝² : CommRing T
inst✝¹ : Algebra R S
inst✝ : Algebra R T
h : Function.Surjective ⇑(algebraMap R T)
x : S
y : R
⊢ ∃ a, includeLeftRingHom a = x ⊗ₜ[R] (algebraMap R T) y

Next tactic:
use y • x
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  introv h x
  skip
  induction x using TensorProduct.induction_on with
  | zero => exact ⟨0, map_zero _⟩
  | tmul x y =>
    obtain ⟨y, rfl⟩ := h y; use y • x; 

Proof state:
case h
R S T : Type u_1
inst✝⁴ : CommRing R
inst✝³ : CommRing S
inst✝² : CommRing T
inst✝¹ : Algebra R S
inst✝ : Algebra R T
h : Function.Surjective ⇑(algebraMap R T)
x : S
y : R
⊢ includeLeftRingHom (y • x) = x ⊗ₜ[R] (algebraMap R T) y

Next tactic:
dsimp
theorem surjective_stableUnderBaseChange : StableUnderBaseChange surjective := by
  refine' StableUnderBaseChange.mk _ surjective_respectsIso _
  classical
  introv h x
  skip
  induction x using TensorProduct.induction_on with
  | zero => exact ⟨0, map_zero _⟩
  | tmul x y =>
    obtain ⟨y, rfl⟩ := h y; use y • x; dsimp
    

Proof state:
case h
R S T : Type u_1
inst✝⁴ : CommRing R
inst✝³ : CommRing S
inst✝² : CommRing T
inst✝¹ : Algebra R S
inst✝ : Algebra R T
h : Function.Surjective ⇑(algebraMap R T)
x : S
y : R
⊢ (y • x) ⊗ₜ[R] 1 = x ⊗ₜ[R] (algebraMap R T) y

Next tactic:
rw [TensorProduct.smul_tmul, Algebra.algebraMap_eq_smul_one]