/-
Copyright (c) 2022 Jannis Limperg. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Jannis Limperg
-/

import Aesop

set_option aesop.check.all true

@[aesop 50%]
inductive Even : Nat → Prop
| zero : Even 0
| plus_two {n} : Even n → Even (n + 2)

structure Even' (n) where
  even : Even n

theorem even'_of_false : False → Even' n
| h => nomatch h

theorem even'_of_even' : Even' n → Even' n :=
  id

-- Once a safe rule is applied, the corresponding goal is marked as inactive
-- and never visited again.
example : Even' 2 := by
  fail_if_success aesop
    (add safe [even'_of_false 0, Even'.mk 1]) (options := { terminal := true })
  fail_if_success aesop
    (add safe [even'_of_even'], unsafe [Even'.mk 100%])
    (options := { maxRuleApplications := 10 })
  aesop
    (add safe [even'_of_false 1, Even'.mk 0])


/-
Copyright (c) 2020 Kenny Lau. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Kenny Lau
-/
import Mathlib.PrePort
import Mathlib.Lean3Lib.init.default
import Mathlib.ring_theory.integral_closure
import Mathlib.ring_theory.valuation.integers
import Mathlib.PostPort

universes u v w

namespace Mathlib

/-!
# Integral elements over the ring of integers of a valution

The ring of integers is integrally closed inside the original ring.
-/

namespace valuation

namespace integers

theorem mem_of_integral {R : Type u} {Γ₀ : Type v} [comm_ring R] [linear_ordered_comm_group_with_zero Γ₀] {v : valuation R Γ₀} {O : Type w} [comm_ring O] [algebra O R] (hv : integers v O) {x : R} (hx : is_integral O x) : x ∈ integer v := sorry

protected theorem integral_closure {R : Type u} {Γ₀ : Type v} [comm_ring R] [linear_ordered_comm_group_with_zero Γ₀] {v : valuation R Γ₀} {O : Type w} [comm_ring O] [algebra O R] (hv : integers v O) : integral_closure O R = ⊥ := sorry


/-
Copyright (c) 2022 Andrew Yang. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Andrew Yang

! This file was ported from Lean 3 source module algebraic_geometry.gluing
! leanprover-community/mathlib commit a9402e0a11843994283cd0a918e61fa51360e26a
! Please do not edit these lines, except to modify the commit id
! if you have ported upstream changes.
-/
import Mathbin.AlgebraicGeometry.PresheafedSpace.Gluing

/-!
# Gluing Schemes

Given a family of gluing data of schemes, we may glue them together.

## Main definitions

* `algebraic_geometry.Scheme.glue_data`: A structure containing the family of gluing data.
* `algebraic_geometry.Scheme.glue_data.glued`: The glued scheme.
    This is defined as the multicoequalizer of `∐ V i j ⇉ ∐ U i`, so that the general colimit API
    can be used.
* `algebraic_geometry.Scheme.glue_data.ι`: The immersion `ι i : U i ⟶ glued` for each `i : J`.
* `algebraic_geometry.Scheme.glue_data.iso_carrier`: The isomorphism between the underlying space
  of the glued scheme and the gluing of the underlying topological spaces.
* `algebraic_geometry.Scheme.open_cover.glue_data`: The glue data associated with an open cover.
* `algebraic_geometry.Scheme.open_cover.from_glue_data`: The canonical morphism
  `𝒰.glue_data.glued ⟶ X`. This has an `is_iso` instance.
* `algebraic_geometry.Scheme.open_cover.glue_morphisms`: We may glue a family of compatible
  morphisms defined on an open cover of a scheme.

## Main results

* `algebraic_geometry.Scheme.glue_data.ι_is_open_immersion`: The map `ι i : U i ⟶ glued`
  is an open immersion for each `i : J`.
* `algebraic_geometry.Scheme.glue_data.ι_jointly_surjective` : The underlying maps of
  `ι i : U i ⟶ glued` are jointly surjective.
* `algebraic_geometry.Scheme.glue_data.V_pullback_cone_is_limit` : `V i j` is the pullback
  (intersection) of `U i` and `U j` over the glued space.
* `algebraic_geometry.Scheme.glue_data.ι_eq_iff_rel` : `ι i x = ι j y` if and only if they coincide
  when restricted to `V i i`.
* `algebraic_geometry.Scheme.glue_data.is_open_iff` : An subset of the glued scheme is open iff
  all its preimages in `U i` are open.

## Implementation details

All the hard work is done in `algebraic_geometry/presheafed_space/gluing.lean` where we glue
presheafed spaces, sheafed spaces, and locally ringed spaces.

-/

noncomputable section

universe u

open TopologicalSpace CategoryTheory Opposite

open CategoryTheory.Limits AlgebraicGeometry.PresheafedSpace

open CategoryTheory.GlueData

namespace AlgebraicGeometry

namespace Scheme

/-- A family of gluing data consists of
1. An index type `J`
2. An scheme `U i` for each `i : J`.
3. An scheme `V i j` for each `i j : J`.
  (Note that this is `J × J → Scheme` rather than `J → J → Scheme` to connect to the
  limits library easier.)
4. An open immersion `f i j : V i j ⟶ U i` for each `i j : ι`.
5. A transition map `t i j : V i j ⟶ V j i` for each `i j : ι`.
such that
6. `f i i` is an isomorphism.
7. `t i i` is the identity.
8. `V i j ×[U i] V i k ⟶ V i j ⟶ V j i` factors through `V j k ×[U j] V j i ⟶ V j i` via some
    `t' : V i j ×[U i] V i k ⟶ V j k ×[U j] V j i`.
9. `t' i j k ≫ t' j k i ≫ t' k i j = 𝟙 _`.

We can then glue the schemes `U i` together by identifying `V i j` with `V j i`, such
that the `U i`'s are open subschemes of the glued space.
-/
@[nolint has_nonempty_instance]
structure GlueData extends CategoryTheory.GlueData Scheme where
  f_open : ∀ i j, IsOpenImmersion (f i j)
#align algebraic_geometry.Scheme.glue_data AlgebraicGeometry.Scheme.GlueData

attribute [instance] glue_data.f_open

namespace GlueData

variable (D : GlueData)

include D

-- mathport name: «expr𝖣»
local notation "𝖣" => D.toGlueData

/-- The glue data of locally ringed spaces spaces associated to a family of glue data of schemes. -/
abbrev toLocallyRingedSpaceGlueData : LocallyRingedSpace.GlueData :=
  { f_open := D.f_open
    toGlueData := 𝖣.mapGlueData forgetToLocallyRingedSpace }
#align algebraic_geometry.Scheme.glue_data.to_LocallyRingedSpace_glue_data AlgebraicGeometry.Scheme.GlueData.toLocallyRingedSpaceGlueData

/-- (Implementation). The glued scheme of a glue data.
This should not be used outside this file. Use `Scheme.glue_data.glued` instead. -/
def gluedScheme : Scheme :=
  by
  apply
    LocallyRingedSpace.is_open_immersion.Scheme D.to_LocallyRingedSpace_glue_data.to_glue_data.glued
  intro x
  obtain ⟨i, y, rfl⟩ := D.to_LocallyRingedSpace_glue_data.ι_jointly_surjective x
  refine' ⟨_, _ ≫ D.to_LocallyRingedSpace_glue_data.to_glue_data.ι i, _⟩
  swap; exact (D.U i).affineCover.map y
  constructor
  · dsimp [-Set.mem_range]
    rw [coe_comp, Set.range_comp]
    refine' Set.mem_image_of_mem _ _
    exact (D.U i).affineCover.Covers y
  · infer_instance
#align algebraic_geometry.Scheme.glue_data.glued_Scheme AlgebraicGeometry.Scheme.GlueData.gluedScheme

instance : CreatesColimit 𝖣.diagram.multispan forgetToLocallyRingedSpace :=
  createsColimitOfFullyFaithfulOfIso D.gluedScheme
    (HasColimit.isoOfNatIso (𝖣.diagramIso forgetToLocallyRingedSpace).symm)

instance : PreservesColimit 𝖣.diagram.multispan forgetToTop :=
  by
  delta forget_to_Top LocallyRingedSpace.forget_to_Top
  infer_instance

instance : HasMulticoequalizer 𝖣.diagram :=
  hasColimit_of_created _ forgetToLocallyRingedSpace

/-- The glued scheme of a glued space. -/
abbrev glued : Scheme :=
  𝖣.glued
#align algebraic_geometry.Scheme.glue_data.glued AlgebraicGeometry.Scheme.GlueData.glued

/-- The immersion from `D.U i` into the glued space. -/
abbrev ι (i : D.J) : D.U i ⟶ D.glued :=
  𝖣.ι i
#align algebraic_geometry.Scheme.glue_data.ι AlgebraicGeometry.Scheme.GlueData.ι

/-- The gluing as sheafed spaces is isomorphic to the gluing as presheafed spaces. -/
abbrev isoLocallyRingedSpace :
    D.glued.toLocallyRingedSpace ≅ D.toLocallyRingedSpaceGlueData.toGlueData.glued :=
  𝖣.gluedIso forgetToLocallyRingedSpace
#align algebraic_geometry.Scheme.glue_data.iso_LocallyRingedSpace AlgebraicGeometry.Scheme.GlueData.isoLocallyRingedSpace

theorem ι_isoLocallyRingedSpace_inv (i : D.J) :
    D.toLocallyRingedSpaceGlueData.toGlueData.ι i ≫ D.isoLocallyRingedSpace.inv = 𝖣.ι i :=
  𝖣.ι_gluedIso_inv forgetToLocallyRingedSpace i
#align algebraic_geometry.Scheme.glue_data.ι_iso_LocallyRingedSpace_inv AlgebraicGeometry.Scheme.GlueData.ι_isoLocallyRingedSpace_inv

instance ι_isOpenImmersion (i : D.J) : IsOpenImmersion (𝖣.ι i) :=
  by
  rw [← D.ι_iso_LocallyRingedSpace_inv]
  infer_instance
#align algebraic_geometry.Scheme.glue_data.ι_is_open_immersion AlgebraicGeometry.Scheme.GlueData.ι_isOpenImmersion

theorem ι_jointly_surjective (x : 𝖣.glued.carrier) :
    ∃ (i : D.J)(y : (D.U i).carrier), (D.ι i).1.base y = x :=
  𝖣.ι_jointly_surjective (forgetToTop ⋙ forget TopCat) x
#align algebraic_geometry.Scheme.glue_data.ι_jointly_surjective AlgebraicGeometry.Scheme.GlueData.ι_jointly_surjective

@[simp, reassoc.1]
theorem glue_condition (i j : D.J) : D.t i j ≫ D.f j i ≫ D.ι j = D.f i j ≫ D.ι i :=
  𝖣.glue_condition i j
#align algebraic_geometry.Scheme.glue_data.glue_condition AlgebraicGeometry.Scheme.GlueData.glue_condition

/-- The pullback cone spanned by `V i j ⟶ U i` and `V i j ⟶ U j`.
This is a pullback diagram (`V_pullback_cone_is_limit`). -/
def vPullbackCone (i j : D.J) : PullbackCone (D.ι i) (D.ι j) :=
  PullbackCone.mk (D.f i j) (D.t i j ≫ D.f j i) (by simp)
#align algebraic_geometry.Scheme.glue_data.V_pullback_cone AlgebraicGeometry.Scheme.GlueData.vPullbackCone

/-- The following diagram is a pullback, i.e. `Vᵢⱼ` is the intersection of `Uᵢ` and `Uⱼ` in `X`.

Vᵢⱼ ⟶ Uᵢ
 |      |
 ↓      ↓
 Uⱼ ⟶ X
-/
def vPullbackConeIsLimit (i j : D.J) : IsLimit (D.vPullbackCone i j) :=
  𝖣.vPullbackConeIsLimitOfMap forgetToLocallyRingedSpace i j
    (D.toLocallyRingedSpaceGlueData.vPullbackConeIsLimit _ _)
#align algebraic_geometry.Scheme.glue_data.V_pullback_cone_is_limit AlgebraicGeometry.Scheme.GlueData.vPullbackConeIsLimit

/-- The underlying topological space of the glued scheme is isomorphic to the gluing of the
underlying spacess -/
def isoCarrier :
    D.glued.carrier ≅
      D.toLocallyRingedSpaceGlueData.toSheafedSpaceGlueData.toPresheafedSpaceGlueData.toTopGlueData.toGlueData.glued :=
  by
  refine' (PresheafedSpace.forget _).mapIso _ ≪≫ glue_data.glued_iso _ (PresheafedSpace.forget _)
  refine'
    SheafedSpace.forget_to_PresheafedSpace.map_iso _ ≪≫ SheafedSpace.glue_data.iso_PresheafedSpace _
  refine'
    LocallyRingedSpace.forget_to_SheafedSpace.map_iso _ ≪≫
      LocallyRingedSpace.glue_data.iso_SheafedSpace _
  exact Scheme.glue_data.iso_LocallyRingedSpace _
#align algebraic_geometry.Scheme.glue_data.iso_carrier AlgebraicGeometry.Scheme.GlueData.isoCarrier

@[simp]
theorem ι_isoCarrier_inv (i : D.J) :
    D.toLocallyRingedSpaceGlueData.toSheafedSpaceGlueData.toPresheafedSpaceGlueData.toTopGlueData.toGlueData.ι
          i ≫
        D.isoCarrier.inv =
      (D.ι i).1.base :=
  by
  delta iso_carrier
  simp only [functor.map_iso_inv, iso.trans_inv, iso.trans_assoc, glue_data.ι_glued_iso_inv_assoc,
    functor.map_iso_trans, category.assoc]
  iterate 3 erw [← comp_base]
  simp_rw [← category.assoc]
  rw [D.to_LocallyRingedSpace_glue_data.to_SheafedSpace_glue_data.ι_iso_PresheafedSpace_inv i]
  erw [D.to_LocallyRingedSpace_glue_data.ι_iso_SheafedSpace_inv i]
  change (_ ≫ D.iso_LocallyRingedSpace.inv).1.base = _
  rw [D.ι_iso_LocallyRingedSpace_inv i]
#align algebraic_geometry.Scheme.glue_data.ι_iso_carrier_inv AlgebraicGeometry.Scheme.GlueData.ι_isoCarrier_inv

/-- An equivalence relation on `Σ i, D.U i` that holds iff `𝖣 .ι i x = 𝖣 .ι j y`.
See `Scheme.gluing_data.ι_eq_iff`. -/
def Rel (a b : Σi, ((D.U i).carrier : Type _)) : Prop :=
  a = b ∨
    ∃ x : (D.V (a.1, b.1)).carrier, (D.f _ _).1.base x = a.2 ∧ (D.t _ _ ≫ D.f _ _).1.base x = b.2
#align algebraic_geometry.Scheme.glue_data.rel AlgebraicGeometry.Scheme.GlueData.Rel

theorem ι_eq_iff (i j : D.J) (x : (D.U i).carrier) (y : (D.U j).carrier) :
    (𝖣.ι i).1.base x = (𝖣.ι j).1.base y ↔ D.Rel ⟨i, x⟩ ⟨j, y⟩ :=
  by
  refine'
    Iff.trans _
      (D.to_LocallyRingedSpace_glue_data.to_SheafedSpace_glue_data.toPresheafedSpaceGlueData.toTopGlueData.ι_eq_iff_rel
        i j x y)
  rw [← ((TopCat.mono_iff_injective D.iso_carrier.inv).mp inferInstance).eq_iff]
  simp_rw [← comp_apply, D.ι_iso_carrier_inv]
#align algebraic_geometry.Scheme.glue_data.ι_eq_iff AlgebraicGeometry.Scheme.GlueData.ι_eq_iff

theorem isOpen_iff (U : Set D.glued.carrier) : IsOpen U ↔ ∀ i, IsOpen ((D.ι i).1.base ⁻¹' U) :=
  by
  rw [← (TopCat.homeoOfIso D.iso_carrier.symm).isOpen_preimage]
  rw [TopCat.GlueData.isOpen_iff]
  apply forall_congr'
  intro i
  erw [← Set.preimage_comp, ← coe_comp, ι_iso_carrier_inv]
#align algebraic_geometry.Scheme.glue_data.is_open_iff AlgebraicGeometry.Scheme.GlueData.isOpen_iff

/-- The open cover of the glued space given by the glue data. -/
def openCover (D : Scheme.GlueData) : OpenCover D.glued
    where
  J := D.J
  obj := D.U
  map := D.ι
  f x := (D.ι_jointly_surjective x).some
  Covers x := ⟨_, (D.ι_jointly_surjective x).choose_spec.choose_spec⟩
#align algebraic_geometry.Scheme.glue_data.open_cover AlgebraicGeometry.Scheme.GlueData.openCover

end GlueData

namespace OpenCover

variable {X : Scheme.{u}} (𝒰 : OpenCover.{u} X)

/-- (Implementation) the transition maps in the glue data associated with an open cover. -/
def gluedCoverT' (x y z : 𝒰.J) :
    pullback (pullback.fst : pullback (𝒰.map x) (𝒰.map y) ⟶ _)
        (pullback.fst : pullback (𝒰.map x) (𝒰.map z) ⟶ _) ⟶
      pullback (pullback.fst : pullback (𝒰.map y) (𝒰.map z) ⟶ _)
        (pullback.fst : pullback (𝒰.map y) (𝒰.map x) ⟶ _) :=
  by
  refine' (pullback_right_pullback_fst_iso _ _ _).Hom ≫ _
  refine' _ ≫ (pullback_symmetry _ _).Hom
  refine' _ ≫ (pullback_right_pullback_fst_iso _ _ _).inv
  refine' pullback.map _ _ _ _ (pullback_symmetry _ _).Hom (𝟙 _) (𝟙 _) _ _
  · simp [pullback.condition]
  · simp
#align algebraic_geometry.Scheme.open_cover.glued_cover_t' AlgebraicGeometry.Scheme.OpenCover.gluedCoverT'

@[simp, reassoc.1]
theorem gluedCoverT'_fst_fst (x y z : 𝒰.J) :
    𝒰.gluedCoverT' x y z ≫ pullback.fst ≫ pullback.fst = pullback.fst ≫ pullback.snd :=
  by
  delta glued_cover_t'
  simp
#align algebraic_geometry.Scheme.open_cover.glued_cover_t'_fst_fst AlgebraicGeometry.Scheme.OpenCover.gluedCoverT'_fst_fst

@[simp, reassoc.1]
theorem gluedCoverT'_fst_snd (x y z : 𝒰.J) :
    gluedCoverT' 𝒰 x y z ≫ pullback.fst ≫ pullback.snd = pullback.snd ≫ pullback.snd :=
  by
  delta glued_cover_t'
  simp
#align algebraic_geometry.Scheme.open_cover.glued_cover_t'_fst_snd AlgebraicGeometry.Scheme.OpenCover.gluedCoverT'_fst_snd

@[simp, reassoc.1]
theorem gluedCoverT'_snd_fst (x y z : 𝒰.J) :
    gluedCoverT' 𝒰 x y z ≫ pullback.snd ≫ pullback.fst = pullback.fst ≫ pullback.snd :=
  by
  delta glued_cover_t'
  simp
#align algebraic_geometry.Scheme.open_cover.glued_cover_t'_snd_fst AlgebraicGeometry.Scheme.OpenCover.gluedCoverT'_snd_fst

@[simp, reassoc.1]
theorem gluedCoverT'_snd_snd (x y z : 𝒰.J) :
    gluedCoverT' 𝒰 x y z ≫ pullback.snd ≫ pullback.snd = pullback.fst ≫ pullback.fst :=
  by
  delta glued_cover_t'
  simp
#align algebraic_geometry.Scheme.open_cover.glued_cover_t'_snd_snd AlgebraicGeometry.Scheme.OpenCover.gluedCoverT'_snd_snd

theorem glued_cover_cocycle_fst (x y z : 𝒰.J) :
    gluedCoverT' 𝒰 x y z ≫ gluedCoverT' 𝒰 y z x ≫ gluedCoverT' 𝒰 z x y ≫ pullback.fst =
      pullback.fst :=
  by apply pullback.hom_ext <;> simp
#align algebraic_geometry.Scheme.open_cover.glued_cover_cocycle_fst AlgebraicGeometry.Scheme.OpenCover.glued_cover_cocycle_fst

theorem glued_cover_cocycle_snd (x y z : 𝒰.J) :
    gluedCoverT' 𝒰 x y z ≫ gluedCoverT' 𝒰 y z x ≫ gluedCoverT' 𝒰 z x y ≫ pullback.snd =
      pullback.snd :=
  by apply pullback.hom_ext <;> simp [pullback.condition]
#align algebraic_geometry.Scheme.open_cover.glued_cover_cocycle_snd AlgebraicGeometry.Scheme.OpenCover.glued_cover_cocycle_snd

theorem glued_cover_cocycle (x y z : 𝒰.J) :
    gluedCoverT' 𝒰 x y z ≫ gluedCoverT' 𝒰 y z x ≫ gluedCoverT' 𝒰 z x y = 𝟙 _ :=
  by
  apply pullback.hom_ext <;> simp_rw [category.id_comp, category.assoc]
  apply glued_cover_cocycle_fst
  apply glued_cover_cocycle_snd
#align algebraic_geometry.Scheme.open_cover.glued_cover_cocycle AlgebraicGeometry.Scheme.OpenCover.glued_cover_cocycle

/-- The glue data associated with an open cover.
The canonical isomorphism `𝒰.glued_cover.glued ⟶ X` is provided by `𝒰.from_glued`. -/
@[simps]
def gluedCover : Scheme.GlueData.{u} where
  J := 𝒰.J
  U := 𝒰.obj
  V := fun ⟨x, y⟩ => pullback (𝒰.map x) (𝒰.map y)
  f x y := pullback.fst
  f_id x := inferInstance
  t x y := (pullbackSymmetry _ _).Hom
  t_id x := by simpa
  t' x y z := gluedCoverT' 𝒰 x y z
  t_fac x y z := by apply pullback.hom_ext <;> simp
  -- The `cocycle` field could have been `by tidy` but lean timeouts.
  cocycle x y z := glued_cover_cocycle 𝒰 x y z
  f_open x := inferInstance
#align algebraic_geometry.Scheme.open_cover.glued_cover AlgebraicGeometry.Scheme.OpenCover.gluedCover

/-- The canonical morphism from the gluing of an open cover of `X` into `X`.
This is an isomorphism, as witnessed by an `is_iso` instance. -/
def fromGlued : 𝒰.gluedCover.glued ⟶ X :=
  by
  fapply multicoequalizer.desc
  exact fun x => 𝒰.map x
  rintro ⟨x, y⟩
  change pullback.fst ≫ _ = ((pullback_symmetry _ _).Hom ≫ pullback.fst) ≫ _
  simpa using pullback.condition
#align algebraic_geometry.Scheme.open_cover.from_glued AlgebraicGeometry.Scheme.OpenCover.fromGlued

@[simp, reassoc.1]
theorem ι_fromGlued (x : 𝒰.J) : 𝒰.gluedCover.ι x ≫ 𝒰.fromGlued = 𝒰.map x :=
  Multicoequalizer.π_desc _ _ _ _ _
#align algebraic_geometry.Scheme.open_cover.ι_from_glued AlgebraicGeometry.Scheme.OpenCover.ι_fromGlued

theorem fromGlued_injective : Function.Injective 𝒰.fromGlued.1.base :=
  by
  intro x y h
  obtain ⟨i, x, rfl⟩ := 𝒰.glued_cover.ι_jointly_surjective x
  obtain ⟨j, y, rfl⟩ := 𝒰.glued_cover.ι_jointly_surjective y
  simp_rw [← comp_apply, ← SheafedSpace.comp_base, ← LocallyRingedSpace.comp_val] at h
  erw [ι_from_glued, ι_from_glued] at h
  let e :=
    (TopCat.pullbackConeIsLimit _ _).conePointUniqueUpToIso
      (is_limit_of_has_pullback_of_preserves_limit Scheme.forget_to_Top (𝒰.map i) (𝒰.map j))
  rw [𝒰.glued_cover.ι_eq_iff]
  right
  use e.hom ⟨⟨x, y⟩, h⟩
  simp_rw [← comp_apply]
  constructor
  · erw [is_limit.cone_point_unique_up_to_iso_hom_comp _ _ walking_cospan.left]
    rfl
  · erw [pullback_symmetry_hom_comp_fst,
      is_limit.cone_point_unique_up_to_iso_hom_comp _ _ walking_cospan.right]
    rfl
#align algebraic_geometry.Scheme.open_cover.from_glued_injective AlgebraicGeometry.Scheme.OpenCover.fromGlued_injective

instance fromGlued_stalk_iso (x : 𝒰.gluedCover.glued.carrier) :
    IsIso (PresheafedSpace.stalkMap 𝒰.fromGlued.val x) :=
  by
  obtain ⟨i, x, rfl⟩ := 𝒰.glued_cover.ι_jointly_surjective x
  have :=
    PresheafedSpace.stalk_map.congr_hom _ _
      (congr_arg LocallyRingedSpace.hom.val <| 𝒰.ι_from_glued i) x
  erw [PresheafedSpace.stalk_map.comp] at this
  rw [← is_iso.eq_comp_inv] at this
  rw [this]
  infer_instance
#align algebraic_geometry.Scheme.open_cover.from_glued_stalk_iso AlgebraicGeometry.Scheme.OpenCover.fromGlued_stalk_iso

theorem fromGlued_open_map : IsOpenMap 𝒰.fromGlued.1.base :=
  by
  intro U hU
  rw [isOpen_iff_forall_mem_open]
  intro x hx
  rw [𝒰.glued_cover.is_open_iff] at hU
  use 𝒰.from_glued.val.base '' U ∩ Set.range (𝒰.map (𝒰.f x)).1.base
  use Set.inter_subset_left _ _
  constructor
  · rw [← Set.image_preimage_eq_inter_range]
    apply show is_open_immersion (𝒰.map (𝒰.f x)) by infer_instance.base_open.IsOpenMap
    convert hU (𝒰.f x) using 1
    rw [← ι_from_glued]
    erw [coe_comp]
    rw [Set.preimage_comp]
    congr 1
    refine' Set.preimage_image_eq _ 𝒰.from_glued_injective
  · exact ⟨hx, 𝒰.covers x⟩
#align algebraic_geometry.Scheme.open_cover.from_glued_open_map AlgebraicGeometry.Scheme.OpenCover.fromGlued_open_map

theorem fromGlued_openEmbedding : OpenEmbedding 𝒰.fromGlued.1.base :=
  openEmbedding_of_continuous_injective_open (by continuity) 𝒰.fromGlued_injective
    𝒰.fromGlued_open_map
#align algebraic_geometry.Scheme.open_cover.from_glued_open_embedding AlgebraicGeometry.Scheme.OpenCover.fromGlued_openEmbedding

instance : Epi 𝒰.fromGlued.val.base :=
  by
  rw [TopCat.epi_iff_surjective]
  intro x
  obtain ⟨y, h⟩ := 𝒰.covers x
  use (𝒰.glued_cover.ι (𝒰.f x)).1.base y
  rw [← comp_apply]
  rw [← 𝒰.ι_from_glued (𝒰.f x)] at h
  exact h

instance fromGlued_open_immersion : IsOpenImmersion 𝒰.fromGlued :=
  SheafedSpace.IsOpenImmersion.of_stalk_iso _ 𝒰.fromGlued_openEmbedding
#align algebraic_geometry.Scheme.open_cover.from_glued_open_immersion AlgebraicGeometry.Scheme.OpenCover.fromGlued_open_immersion

instance : IsIso 𝒰.fromGlued :=
  by
  apply
    is_iso_of_reflects_iso _
      (Scheme.forget_to_LocallyRingedSpace ⋙
        LocallyRingedSpace.forget_to_SheafedSpace ⋙ SheafedSpace.forget_to_PresheafedSpace)
  change @is_iso (PresheafedSpace _) _ _ _ 𝒰.from_glued.val
  apply PresheafedSpace.is_open_immersion.to_iso

/-- Given an open cover of `X`, and a morphism `𝒰.obj x ⟶ Y` for each open subscheme in the cover,
such that these morphisms are compatible in the intersection (pullback), we may glue the morphisms
together into a morphism `X ⟶ Y`.

Note:
If `X` is exactly (defeq to) the gluing of `U i`, then using `multicoequalizer.desc` suffices.
-/
def glueMorphisms {Y : Scheme} (f : ∀ x, 𝒰.obj x ⟶ Y)
    (hf : ∀ x y, (pullback.fst : pullback (𝒰.map x) (𝒰.map y) ⟶ _) ≫ f x = pullback.snd ≫ f y) :
    X ⟶ Y := by
  refine' inv 𝒰.from_glued ≫ _
  fapply multicoequalizer.desc
  exact f
  rintro ⟨i, j⟩
  change pullback.fst ≫ f i = (_ ≫ _) ≫ f j
  erw [pullback_symmetry_hom_comp_fst]
  exact hf i j
#align algebraic_geometry.Scheme.open_cover.glue_morphisms AlgebraicGeometry.Scheme.OpenCover.glueMorphisms

@[simp, reassoc.1]
theorem ι_glueMorphisms {Y : Scheme} (f : ∀ x, 𝒰.obj x ⟶ Y)
    (hf : ∀ x y, (pullback.fst : pullback (𝒰.map x) (𝒰.map y) ⟶ _) ≫ f x = pullback.snd ≫ f y)
    (x : 𝒰.J) : 𝒰.map x ≫ 𝒰.glueMorphisms f hf = f x :=
  by
  rw [← ι_from_glued, category.assoc]
  erw [is_iso.hom_inv_id_assoc, multicoequalizer.π_desc]
#align algebraic_geometry.Scheme.open_cover.ι_glue_morphisms AlgebraicGeometry.Scheme.OpenCover.ι_glueMorphisms

theorem hom_ext {Y : Scheme} (f₁ f₂ : X ⟶ Y) (h : ∀ x, 𝒰.map x ≫ f₁ = 𝒰.map x ≫ f₂) : f₁ = f₂ :=
  by
  rw [← cancel_epi 𝒰.from_glued]
  apply multicoequalizer.hom_ext
  intro x
  erw [multicoequalizer.π_desc_assoc]
  erw [multicoequalizer.π_desc_assoc]
  exact h x
#align algebraic_geometry.Scheme.open_cover.hom_ext AlgebraicGeometry.Scheme.OpenCover.hom_ext

end OpenCover

end Scheme

end AlgebraicGeometry


/-
Copyright (c) 2020 Kenny Lau. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Kenny Lau

! This file was ported from Lean 3 source module algebra.polynomial.group_ring_action
! leanprover-community/mathlib commit 10bf4f825ad729c5653adc039dafa3622e7f93c9
! Please do not edit these lines, except to modify the commit id
! if you have ported upstream changes.
-/
import Mathbin.Algebra.GroupRingAction.Basic
import Mathbin.Algebra.Hom.GroupAction
import Mathbin.Data.Polynomial.AlgebraMap
import Mathbin.Data.Polynomial.Monic
import Mathbin.GroupTheory.GroupAction.Quotient

/-!
# Group action on rings applied to polynomials

> THIS FILE IS SYNCHRONIZED WITH MATHLIB4.
> Any changes to this file require a corresponding PR to mathlib4.

This file contains instances and definitions relating `mul_semiring_action` to `polynomial`.
-/

variable (M : Type _) [Monoid M]

open Polynomial

namespace Polynomial

variable (R : Type _) [Semiring R]

variable {M}

/- warning: polynomial.smul_eq_map -> Polynomial.smul_eq_map is a dubious translation:
lean 3 declaration is
  forall {M : Type.{u1}} [_inst_1 : Monoid.{u1} M] (R : Type.{u2}) [_inst_2 : Semiring.{u2} R] [_inst_3 : MulSemiringAction.{u1, u2} M R _inst_1 _inst_2] (m : M), Eq.{succ u2} ((Polynomial.{u2} R _inst_2) -> (Polynomial.{u2} R _inst_2)) (SMul.smul.{u1, u2} M (Polynomial.{u2} R _inst_2) (SMulZeroClass.toHasSmul.{u1, u2} M (Polynomial.{u2} R _inst_2) (Polynomial.zero.{u2} R _inst_2) (Polynomial.smulZeroClass.{u2, u1} R _inst_2 M (DistribSMul.toSmulZeroClass.{u1, u2} M R (AddMonoid.toAddZeroClass.{u2} R (AddMonoidWithOne.toAddMonoid.{u2} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} R (NonAssocSemiring.toAddCommMonoidWithOne.{u2} R (Semiring.toNonAssocSemiring.{u2} R _inst_2))))) (DistribMulAction.toDistribSMul.{u1, u2} M R _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} R (NonAssocSemiring.toAddCommMonoidWithOne.{u2} R (Semiring.toNonAssocSemiring.{u2} R _inst_2)))) (MulSemiringAction.toDistribMulAction.{u1, u2} M R _inst_1 _inst_2 _inst_3))))) m) (Polynomial.map.{u2, u2} R R _inst_2 _inst_2 (MulSemiringAction.toRingHom.{u2, u1} M _inst_1 R _inst_2 _inst_3 m))
but is expected to have type
  forall {M : Type.{u2}} [_inst_1 : Monoid.{u2} M] (R : Type.{u1}) [_inst_2 : Semiring.{u1} R] [_inst_3 : MulSemiringAction.{u2, u1} M R _inst_1 _inst_2] (m : M), Eq.{succ u1} ((Polynomial.{u1} R _inst_2) -> (Polynomial.{u1} R _inst_2)) (HSMul.hSMul.{u2, u1, u1} M (Polynomial.{u1} R _inst_2) (Polynomial.{u1} R _inst_2) (instHSMul.{u2, u1} M (Polynomial.{u1} R _inst_2) (SMulZeroClass.toSMul.{u2, u1} M (Polynomial.{u1} R _inst_2) (Polynomial.zero.{u1} R _inst_2) (Polynomial.smulZeroClass.{u1, u2} R _inst_2 M (DistribSMul.toSMulZeroClass.{u2, u1} M R (AddMonoid.toAddZeroClass.{u1} R (AddMonoidWithOne.toAddMonoid.{u1} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} R (NonAssocSemiring.toAddCommMonoidWithOne.{u1} R (Semiring.toNonAssocSemiring.{u1} R _inst_2))))) (DistribMulAction.toDistribSMul.{u2, u1} M R _inst_1 (AddMonoidWithOne.toAddMonoid.{u1} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} R (NonAssocSemiring.toAddCommMonoidWithOne.{u1} R (Semiring.toNonAssocSemiring.{u1} R _inst_2)))) (MulSemiringAction.toDistribMulAction.{u2, u1} M R _inst_1 _inst_2 _inst_3)))))) m) (Polynomial.map.{u1, u1} R R _inst_2 _inst_2 (MulSemiringAction.toRingHom.{u1, u2} M _inst_1 R _inst_2 _inst_3 m))
Case conversion may be inaccurate. Consider using '#align polynomial.smul_eq_map Polynomial.smul_eq_mapₓ'. -/
theorem smul_eq_map [MulSemiringAction M R] (m : M) :
    (· • ·) m = map (MulSemiringAction.toRingHom M R m) :=
  by
  suffices
    DistribMulAction.toAddMonoidHom R[X] m =
      (map_ring_hom (MulSemiringAction.toRingHom M R m)).toAddMonoidHom
    by
    ext1 r
    exact AddMonoidHom.congr_fun this r
  ext (n r) : 2
  change m • monomial n r = map (MulSemiringAction.toRingHom M R m) (monomial n r)
  simpa only [Polynomial.map_monomial, Polynomial.smul_monomial]
#align polynomial.smul_eq_map Polynomial.smul_eq_map

variable (M)

noncomputable instance [MulSemiringAction M R] : MulSemiringAction M R[X] :=
  { Polynomial.distribMulAction with
    smul := (· • ·)
    smul_one := fun m =>
      (smul_eq_map R m).symm ▸ Polynomial.map_one (MulSemiringAction.toRingHom M R m)
    smul_mul := fun m p q =>
      (smul_eq_map R m).symm ▸ Polynomial.map_mul (MulSemiringAction.toRingHom M R m) }

variable {M R}

variable [MulSemiringAction M R]

/- warning: polynomial.smul_X -> Polynomial.smul_X is a dubious translation:
lean 3 declaration is
  forall {M : Type.{u1}} [_inst_1 : Monoid.{u1} M] {R : Type.{u2}} [_inst_2 : Semiring.{u2} R] [_inst_3 : MulSemiringAction.{u1, u2} M R _inst_1 _inst_2] (m : M), Eq.{succ u2} (Polynomial.{u2} R _inst_2) (SMul.smul.{u1, u2} M (Polynomial.{u2} R _inst_2) (SMulZeroClass.toHasSmul.{u1, u2} M (Polynomial.{u2} R _inst_2) (Polynomial.zero.{u2} R _inst_2) (Polynomial.smulZeroClass.{u2, u1} R _inst_2 M (DistribSMul.toSmulZeroClass.{u1, u2} M R (AddMonoid.toAddZeroClass.{u2} R (AddMonoidWithOne.toAddMonoid.{u2} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} R (NonAssocSemiring.toAddCommMonoidWithOne.{u2} R (Semiring.toNonAssocSemiring.{u2} R _inst_2))))) (DistribMulAction.toDistribSMul.{u1, u2} M R _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} R (NonAssocSemiring.toAddCommMonoidWithOne.{u2} R (Semiring.toNonAssocSemiring.{u2} R _inst_2)))) (MulSemiringAction.toDistribMulAction.{u1, u2} M R _inst_1 _inst_2 _inst_3))))) m (Polynomial.X.{u2} R _inst_2)) (Polynomial.X.{u2} R _inst_2)
but is expected to have type
  forall {M : Type.{u1}} [_inst_1 : Monoid.{u1} M] {R : Type.{u2}} [_inst_2 : Semiring.{u2} R] [_inst_3 : MulSemiringAction.{u1, u2} M R _inst_1 _inst_2] (m : M), Eq.{succ u2} (Polynomial.{u2} R _inst_2) (HSMul.hSMul.{u1, u2, u2} M (Polynomial.{u2} R _inst_2) (Polynomial.{u2} R _inst_2) (instHSMul.{u1, u2} M (Polynomial.{u2} R _inst_2) (SMulZeroClass.toSMul.{u1, u2} M (Polynomial.{u2} R _inst_2) (Polynomial.zero.{u2} R _inst_2) (Polynomial.smulZeroClass.{u2, u1} R _inst_2 M (DistribSMul.toSMulZeroClass.{u1, u2} M R (AddMonoid.toAddZeroClass.{u2} R (AddMonoidWithOne.toAddMonoid.{u2} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} R (NonAssocSemiring.toAddCommMonoidWithOne.{u2} R (Semiring.toNonAssocSemiring.{u2} R _inst_2))))) (DistribMulAction.toDistribSMul.{u1, u2} M R _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} R (NonAssocSemiring.toAddCommMonoidWithOne.{u2} R (Semiring.toNonAssocSemiring.{u2} R _inst_2)))) (MulSemiringAction.toDistribMulAction.{u1, u2} M R _inst_1 _inst_2 _inst_3)))))) m (Polynomial.X.{u2} R _inst_2)) (Polynomial.X.{u2} R _inst_2)
Case conversion may be inaccurate. Consider using '#align polynomial.smul_X Polynomial.smul_Xₓ'. -/
@[simp]
theorem smul_X (m : M) : (m • X : R[X]) = X :=
  (smul_eq_map R m).symm ▸ map_X _
#align polynomial.smul_X Polynomial.smul_X

variable (S : Type _) [CommSemiring S] [MulSemiringAction M S]

/- warning: polynomial.smul_eval_smul -> Polynomial.smul_eval_smul is a dubious translation:
lean 3 declaration is
  forall {M : Type.{u1}} [_inst_1 : Monoid.{u1} M] (S : Type.{u2}) [_inst_4 : CommSemiring.{u2} S] [_inst_5 : MulSemiringAction.{u1, u2} M S _inst_1 (CommSemiring.toSemiring.{u2} S _inst_4)] (m : M) (f : Polynomial.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (x : S), Eq.{succ u2} S (Polynomial.eval.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4) (SMul.smul.{u1, u2} M S (SMulZeroClass.toHasSmul.{u1, u2} M S (AddZeroClass.toHasZero.{u2} S (AddMonoid.toAddZeroClass.{u2} S (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4))))))) (DistribSMul.toSmulZeroClass.{u1, u2} M S (AddMonoid.toAddZeroClass.{u2} S (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u1, u2} M S _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u1, u2} M S _inst_1 (CommSemiring.toSemiring.{u2} S _inst_4) _inst_5)))) m x) (SMul.smul.{u1, u2} M (Polynomial.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (SMulZeroClass.toHasSmul.{u1, u2} M (Polynomial.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (Polynomial.zero.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (Polynomial.smulZeroClass.{u2, u1} S (CommSemiring.toSemiring.{u2} S _inst_4) M (DistribSMul.toSmulZeroClass.{u1, u2} M S (AddMonoid.toAddZeroClass.{u2} S (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u1, u2} M S _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u1, u2} M S _inst_1 (CommSemiring.toSemiring.{u2} S _inst_4) _inst_5))))) m f)) (SMul.smul.{u1, u2} M S (SMulZeroClass.toHasSmul.{u1, u2} M S (AddZeroClass.toHasZero.{u2} S (AddMonoid.toAddZeroClass.{u2} S (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4))))))) (DistribSMul.toSmulZeroClass.{u1, u2} M S (AddMonoid.toAddZeroClass.{u2} S (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u1, u2} M S _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u1, u2} M S _inst_1 (CommSemiring.toSemiring.{u2} S _inst_4) _inst_5)))) m (Polynomial.eval.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4) x f))
but is expected to have type
  forall {M : Type.{u1}} [_inst_1 : Monoid.{u1} M] (S : Type.{u2}) [_inst_4 : CommSemiring.{u2} S] [_inst_5 : MulSemiringAction.{u1, u2} M S _inst_1 (CommSemiring.toSemiring.{u2} S _inst_4)] (m : M) (f : Polynomial.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (x : S), Eq.{succ u2} S (Polynomial.eval.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4) (HSMul.hSMul.{u1, u2, u2} M S S (instHSMul.{u1, u2} M S (SMulZeroClass.toSMul.{u1, u2} M S (CommMonoidWithZero.toZero.{u2} S (CommSemiring.toCommMonoidWithZero.{u2} S _inst_4)) (DistribSMul.toSMulZeroClass.{u1, u2} M S (AddMonoid.toAddZeroClass.{u2} S (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u1, u2} M S _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u1, u2} M S _inst_1 (CommSemiring.toSemiring.{u2} S _inst_4) _inst_5))))) m x) (HSMul.hSMul.{u1, u2, u2} M (Polynomial.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (Polynomial.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (instHSMul.{u1, u2} M (Polynomial.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (SMulZeroClass.toSMul.{u1, u2} M (Polynomial.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (Polynomial.zero.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)) (Polynomial.smulZeroClass.{u2, u1} S (CommSemiring.toSemiring.{u2} S _inst_4) M (DistribSMul.toSMulZeroClass.{u1, u2} M S (AddMonoid.toAddZeroClass.{u2} S (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u1, u2} M S _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u1, u2} M S _inst_1 (CommSemiring.toSemiring.{u2} S _inst_4) _inst_5)))))) m f)) (HSMul.hSMul.{u1, u2, u2} M S S (instHSMul.{u1, u2} M S (SMulZeroClass.toSMul.{u1, u2} M S (CommMonoidWithZero.toZero.{u2} S (CommSemiring.toCommMonoidWithZero.{u2} S _inst_4)) (DistribSMul.toSMulZeroClass.{u1, u2} M S (AddMonoid.toAddZeroClass.{u2} S (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u1, u2} M S _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} S (NonAssocSemiring.toAddCommMonoidWithOne.{u2} S (Semiring.toNonAssocSemiring.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u1, u2} M S _inst_1 (CommSemiring.toSemiring.{u2} S _inst_4) _inst_5))))) m (Polynomial.eval.{u2} S (CommSemiring.toSemiring.{u2} S _inst_4) x f))
Case conversion may be inaccurate. Consider using '#align polynomial.smul_eval_smul Polynomial.smul_eval_smulₓ'. -/
theorem smul_eval_smul (m : M) (f : S[X]) (x : S) : (m • f).eval (m • x) = m • f.eval x :=
  Polynomial.induction_on f (fun r => by rw [smul_C, eval_C, eval_C])
    (fun f g ihf ihg => by rw [smul_add, eval_add, ihf, ihg, eval_add, smul_add]) fun n r ih => by
    rw [smul_mul', smul_pow', smul_C, smul_X, eval_mul, eval_C, eval_pow, eval_X, eval_mul, eval_C,
      eval_pow, eval_X, smul_mul', smul_pow']
#align polynomial.smul_eval_smul Polynomial.smul_eval_smul

variable (G : Type _) [Group G]

/- warning: polynomial.eval_smul' -> Polynomial.eval_smul' is a dubious translation:
lean 3 declaration is
  forall (S : Type.{u1}) [_inst_4 : CommSemiring.{u1} S] (G : Type.{u2}) [_inst_6 : Group.{u2} G] [_inst_7 : MulSemiringAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4)] (g : G) (f : Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (x : S), Eq.{succ u1} S (Polynomial.eval.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4) (SMul.smul.{u2, u1} G S (SMulZeroClass.toHasSmul.{u2, u1} G S (AddZeroClass.toHasZero.{u1} S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))))) (DistribSMul.toSmulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7)))) g x) f) (SMul.smul.{u2, u1} G S (SMulZeroClass.toHasSmul.{u2, u1} G S (AddZeroClass.toHasZero.{u1} S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))))) (DistribSMul.toSmulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7)))) g (Polynomial.eval.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4) x (SMul.smul.{u2, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (SMulZeroClass.toHasSmul.{u2, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.zero.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.smulZeroClass.{u1, u2} S (CommSemiring.toSemiring.{u1} S _inst_4) G (DistribSMul.toSmulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7))))) (Inv.inv.{u2} G (DivInvMonoid.toHasInv.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) g) f)))
but is expected to have type
  forall (S : Type.{u1}) [_inst_4 : CommSemiring.{u1} S] (G : Type.{u2}) [_inst_6 : Group.{u2} G] [_inst_7 : MulSemiringAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4)] (g : G) (f : Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (x : S), Eq.{succ u1} S (Polynomial.eval.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4) (HSMul.hSMul.{u2, u1, u1} G S S (instHSMul.{u2, u1} G S (SMulZeroClass.toSMul.{u2, u1} G S (CommMonoidWithZero.toZero.{u1} S (CommSemiring.toCommMonoidWithZero.{u1} S _inst_4)) (DistribSMul.toSMulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7))))) g x) f) (HSMul.hSMul.{u2, u1, u1} G S S (instHSMul.{u2, u1} G S (SMulZeroClass.toSMul.{u2, u1} G S (CommMonoidWithZero.toZero.{u1} S (CommSemiring.toCommMonoidWithZero.{u1} S _inst_4)) (DistribSMul.toSMulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7))))) g (Polynomial.eval.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4) x (HSMul.hSMul.{u2, u1, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (instHSMul.{u2, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (SMulZeroClass.toSMul.{u2, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.zero.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.smulZeroClass.{u1, u2} S (CommSemiring.toSemiring.{u1} S _inst_4) G (DistribSMul.toSMulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7)))))) (Inv.inv.{u2} G (InvOneClass.toInv.{u2} G (DivInvOneMonoid.toInvOneClass.{u2} G (DivisionMonoid.toDivInvOneMonoid.{u2} G (Group.toDivisionMonoid.{u2} G _inst_6)))) g) f)))
Case conversion may be inaccurate. Consider using '#align polynomial.eval_smul' Polynomial.eval_smul'ₓ'. -/
theorem eval_smul' [MulSemiringAction G S] (g : G) (f : S[X]) (x : S) :
    f.eval (g • x) = g • (g⁻¹ • f).eval x := by rw [← smul_eval_smul, smul_inv_smul]
#align polynomial.eval_smul' Polynomial.eval_smul'

/- warning: polynomial.smul_eval -> Polynomial.smul_eval is a dubious translation:
lean 3 declaration is
  forall (S : Type.{u1}) [_inst_4 : CommSemiring.{u1} S] (G : Type.{u2}) [_inst_6 : Group.{u2} G] [_inst_7 : MulSemiringAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4)] (g : G) (f : Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (x : S), Eq.{succ u1} S (Polynomial.eval.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4) x (SMul.smul.{u2, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (SMulZeroClass.toHasSmul.{u2, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.zero.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.smulZeroClass.{u1, u2} S (CommSemiring.toSemiring.{u1} S _inst_4) G (DistribSMul.toSmulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7))))) g f)) (SMul.smul.{u2, u1} G S (SMulZeroClass.toHasSmul.{u2, u1} G S (AddZeroClass.toHasZero.{u1} S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))))) (DistribSMul.toSmulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7)))) g (Polynomial.eval.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4) (SMul.smul.{u2, u1} G S (SMulZeroClass.toHasSmul.{u2, u1} G S (AddZeroClass.toHasZero.{u1} S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))))) (DistribSMul.toSmulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7)))) (Inv.inv.{u2} G (DivInvMonoid.toHasInv.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) g) x) f))
but is expected to have type
  forall (S : Type.{u1}) [_inst_4 : CommSemiring.{u1} S] (G : Type.{u2}) [_inst_6 : Group.{u2} G] [_inst_7 : MulSemiringAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4)] (g : G) (f : Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (x : S), Eq.{succ u1} S (Polynomial.eval.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4) x (HSMul.hSMul.{u2, u1, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (instHSMul.{u2, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (SMulZeroClass.toSMul.{u2, u1} G (Polynomial.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.zero.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)) (Polynomial.smulZeroClass.{u1, u2} S (CommSemiring.toSemiring.{u1} S _inst_4) G (DistribSMul.toSMulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7)))))) g f)) (HSMul.hSMul.{u2, u1, u1} G S S (instHSMul.{u2, u1} G S (SMulZeroClass.toSMul.{u2, u1} G S (CommMonoidWithZero.toZero.{u1} S (CommSemiring.toCommMonoidWithZero.{u1} S _inst_4)) (DistribSMul.toSMulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7))))) g (Polynomial.eval.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4) (HSMul.hSMul.{u2, u1, u1} G S S (instHSMul.{u2, u1} G S (SMulZeroClass.toSMul.{u2, u1} G S (CommMonoidWithZero.toZero.{u1} S (CommSemiring.toCommMonoidWithZero.{u1} S _inst_4)) (DistribSMul.toSMulZeroClass.{u2, u1} G S (AddMonoid.toAddZeroClass.{u1} S (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4)))))) (DistribMulAction.toDistribSMul.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (AddMonoidWithOne.toAddMonoid.{u1} S (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} S (NonAssocSemiring.toAddCommMonoidWithOne.{u1} S (Semiring.toNonAssocSemiring.{u1} S (CommSemiring.toSemiring.{u1} S _inst_4))))) (MulSemiringAction.toDistribMulAction.{u2, u1} G S (DivInvMonoid.toMonoid.{u2} G (Group.toDivInvMonoid.{u2} G _inst_6)) (CommSemiring.toSemiring.{u1} S _inst_4) _inst_7))))) (Inv.inv.{u2} G (InvOneClass.toInv.{u2} G (DivInvOneMonoid.toInvOneClass.{u2} G (DivisionMonoid.toDivInvOneMonoid.{u2} G (Group.toDivisionMonoid.{u2} G _inst_6)))) g) x) f))
Case conversion may be inaccurate. Consider using '#align polynomial.smul_eval Polynomial.smul_evalₓ'. -/
theorem smul_eval [MulSemiringAction G S] (g : G) (f : S[X]) (x : S) :
    (g • f).eval x = g • f.eval (g⁻¹ • x) := by rw [← smul_eval_smul, smul_inv_smul]
#align polynomial.smul_eval Polynomial.smul_eval

end Polynomial

section CommRing

variable (G : Type _) [Group G] [Fintype G]

variable (R : Type _) [CommRing R] [MulSemiringAction G R]

open MulAction

open Classical

#print prodXSubSmul /-
/-- the product of `(X - g • x)` over distinct `g • x`. -/
noncomputable def prodXSubSmul (x : R) : R[X] :=
  (Finset.univ : Finset (G ⧸ MulAction.stabilizer G x)).Prod fun g =>
    Polynomial.X - Polynomial.C (ofQuotientStabilizer G x g)
#align prod_X_sub_smul prodXSubSmul
-/

#print prodXSubSmul.monic /-
theorem prodXSubSmul.monic (x : R) : (prodXSubSmul G R x).Monic :=
  Polynomial.monic_prod_of_monic _ _ fun g _ => Polynomial.monic_X_sub_C _
#align prod_X_sub_smul.monic prodXSubSmul.monic
-/

/- warning: prod_X_sub_smul.eval -> prodXSubSmul.eval is a dubious translation:
lean 3 declaration is
  forall (G : Type.{u1}) [_inst_2 : Group.{u1} G] [_inst_3 : Fintype.{u1} G] (R : Type.{u2}) [_inst_4 : CommRing.{u2} R] [_inst_5 : MulSemiringAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))] (x : R), Eq.{succ u2} R (Polynomial.eval.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) x (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x)) (OfNat.ofNat.{u2} R 0 (OfNat.mk.{u2} R 0 (Zero.zero.{u2} R (MulZeroClass.toHasZero.{u2} R (NonUnitalNonAssocSemiring.toMulZeroClass.{u2} R (NonUnitalNonAssocRing.toNonUnitalNonAssocSemiring.{u2} R (NonAssocRing.toNonUnitalNonAssocRing.{u2} R (Ring.toNonAssocRing.{u2} R (CommRing.toRing.{u2} R _inst_4)))))))))
but is expected to have type
  forall (G : Type.{u1}) [_inst_2 : Group.{u1} G] [_inst_3 : Fintype.{u1} G] (R : Type.{u2}) [_inst_4 : CommRing.{u2} R] [_inst_5 : MulSemiringAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))] (x : R), Eq.{succ u2} R (Polynomial.eval.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) x (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x)) (OfNat.ofNat.{u2} R 0 (Zero.toOfNat0.{u2} R (CommMonoidWithZero.toZero.{u2} R (CommSemiring.toCommMonoidWithZero.{u2} R (CommRing.toCommSemiring.{u2} R _inst_4)))))
Case conversion may be inaccurate. Consider using '#align prod_X_sub_smul.eval prodXSubSmul.evalₓ'. -/
theorem prodXSubSmul.eval (x : R) : (prodXSubSmul G R x).eval x = 0 :=
  (MonoidHom.map_prod ((Polynomial.aeval x).toRingHom.toMonoidHom : R[X] →* R) _ _).trans <|
    Finset.prod_eq_zero (Finset.mem_univ <| QuotientGroup.mk 1) <| by simp
#align prod_X_sub_smul.eval prodXSubSmul.eval

/- warning: prod_X_sub_smul.smul -> prodXSubSmul.smul is a dubious translation:
lean 3 declaration is
  forall (G : Type.{u1}) [_inst_2 : Group.{u1} G] [_inst_3 : Fintype.{u1} G] (R : Type.{u2}) [_inst_4 : CommRing.{u2} R] [_inst_5 : MulSemiringAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))] (x : R) (g : G), Eq.{succ u2} (Polynomial.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (SMul.smul.{u1, u2} G (Polynomial.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (SMulZeroClass.toHasSmul.{u1, u2} G (Polynomial.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (Polynomial.zero.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (Polynomial.smulZeroClass.{u2, u1} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) G (DistribSMul.toSmulZeroClass.{u1, u2} G R (AddMonoid.toAddZeroClass.{u2} R (AddMonoidWithOne.toAddMonoid.{u2} R (AddGroupWithOne.toAddMonoidWithOne.{u2} R (AddCommGroupWithOne.toAddGroupWithOne.{u2} R (Ring.toAddCommGroupWithOne.{u2} R (CommRing.toRing.{u2} R _inst_4)))))) (DistribMulAction.toDistribSMul.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (AddMonoidWithOne.toAddMonoid.{u2} R (AddGroupWithOne.toAddMonoidWithOne.{u2} R (AddCommGroupWithOne.toAddGroupWithOne.{u2} R (Ring.toAddCommGroupWithOne.{u2} R (CommRing.toRing.{u2} R _inst_4))))) (MulSemiringAction.toDistribMulAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) _inst_5))))) g (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x)) (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x)
but is expected to have type
  forall (G : Type.{u1}) [_inst_2 : Group.{u1} G] [_inst_3 : Fintype.{u1} G] (R : Type.{u2}) [_inst_4 : CommRing.{u2} R] [_inst_5 : MulSemiringAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))] (x : R) (g : G), Eq.{succ u2} (Polynomial.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (HSMul.hSMul.{u1, u2, u2} G (Polynomial.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (Polynomial.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (instHSMul.{u1, u2} G (Polynomial.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (SMulZeroClass.toSMul.{u1, u2} G (Polynomial.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (Polynomial.zero.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))) (Polynomial.smulZeroClass.{u2, u1} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) G (DistribSMul.toSMulZeroClass.{u1, u2} G R (AddMonoid.toAddZeroClass.{u2} R (AddMonoidWithOne.toAddMonoid.{u2} R (AddGroupWithOne.toAddMonoidWithOne.{u2} R (Ring.toAddGroupWithOne.{u2} R (CommRing.toRing.{u2} R _inst_4))))) (DistribMulAction.toDistribSMul.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (AddMonoidWithOne.toAddMonoid.{u2} R (AddGroupWithOne.toAddMonoidWithOne.{u2} R (Ring.toAddGroupWithOne.{u2} R (CommRing.toRing.{u2} R _inst_4)))) (MulSemiringAction.toDistribMulAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) _inst_5)))))) g (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x)) (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x)
Case conversion may be inaccurate. Consider using '#align prod_X_sub_smul.smul prodXSubSmul.smulₓ'. -/
theorem prodXSubSmul.smul (x : R) (g : G) : g • prodXSubSmul G R x = prodXSubSmul G R x :=
  Finset.smul_prod.trans <|
    Fintype.prod_bijective _ (MulAction.bijective g) _ _ fun g' => by
      rw [of_quotient_stabilizer_smul, smul_sub, Polynomial.smul_X, Polynomial.smul_C]
#align prod_X_sub_smul.smul prodXSubSmul.smul

/- warning: prod_X_sub_smul.coeff -> prodXSubSmul.coeff is a dubious translation:
lean 3 declaration is
  forall (G : Type.{u1}) [_inst_2 : Group.{u1} G] [_inst_3 : Fintype.{u1} G] (R : Type.{u2}) [_inst_4 : CommRing.{u2} R] [_inst_5 : MulSemiringAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))] (x : R) (g : G) (n : Nat), Eq.{succ u2} R (SMul.smul.{u1, u2} G R (SMulZeroClass.toHasSmul.{u1, u2} G R (AddZeroClass.toHasZero.{u2} R (AddMonoid.toAddZeroClass.{u2} R (AddMonoidWithOne.toAddMonoid.{u2} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} R (NonAssocSemiring.toAddCommMonoidWithOne.{u2} R (Semiring.toNonAssocSemiring.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)))))))) (DistribSMul.toSmulZeroClass.{u1, u2} G R (AddMonoid.toAddZeroClass.{u2} R (AddMonoidWithOne.toAddMonoid.{u2} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} R (NonAssocSemiring.toAddCommMonoidWithOne.{u2} R (Semiring.toNonAssocSemiring.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))))))) (DistribMulAction.toDistribSMul.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (AddMonoidWithOne.toAddMonoid.{u2} R (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} R (NonAssocSemiring.toAddCommMonoidWithOne.{u2} R (Semiring.toNonAssocSemiring.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)))))) (MulSemiringAction.toDistribMulAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) _inst_5)))) g (Polynomial.coeff.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x) n)) (Polynomial.coeff.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x) n)
but is expected to have type
  forall (G : Type.{u1}) [_inst_2 : Group.{u1} G] [_inst_3 : Fintype.{u1} G] (R : Type.{u2}) [_inst_4 : CommRing.{u2} R] [_inst_5 : MulSemiringAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4))] (x : R) (g : G) (n : Nat), Eq.{succ u2} R (HSMul.hSMul.{u1, u2, u2} G R R (instHSMul.{u1, u2} G R (SMulZeroClass.toSMul.{u1, u2} G R (CommMonoidWithZero.toZero.{u2} R (CommSemiring.toCommMonoidWithZero.{u2} R (CommRing.toCommSemiring.{u2} R _inst_4))) (DistribSMul.toSMulZeroClass.{u1, u2} G R (AddMonoid.toAddZeroClass.{u2} R (AddMonoidWithOne.toAddMonoid.{u2} R (AddGroupWithOne.toAddMonoidWithOne.{u2} R (Ring.toAddGroupWithOne.{u2} R (CommRing.toRing.{u2} R _inst_4))))) (DistribMulAction.toDistribSMul.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (AddMonoidWithOne.toAddMonoid.{u2} R (AddGroupWithOne.toAddMonoidWithOne.{u2} R (Ring.toAddGroupWithOne.{u2} R (CommRing.toRing.{u2} R _inst_4)))) (MulSemiringAction.toDistribMulAction.{u1, u2} G R (DivInvMonoid.toMonoid.{u1} G (Group.toDivInvMonoid.{u1} G _inst_2)) (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) _inst_5))))) g (Polynomial.coeff.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x) n)) (Polynomial.coeff.{u2} R (Ring.toSemiring.{u2} R (CommRing.toRing.{u2} R _inst_4)) (prodXSubSmul.{u1, u2} G _inst_2 _inst_3 R _inst_4 _inst_5 x) n)
Case conversion may be inaccurate. Consider using '#align prod_X_sub_smul.coeff prodXSubSmul.coeffₓ'. -/
theorem prodXSubSmul.coeff (x : R) (g : G) (n : ℕ) :
    g • (prodXSubSmul G R x).coeff n = (prodXSubSmul G R x).coeff n := by
  rw [← Polynomial.coeff_smul, prodXSubSmul.smul]
#align prod_X_sub_smul.coeff prodXSubSmul.coeff

end CommRing

namespace MulSemiringActionHom

variable {M}

variable {P : Type _} [CommSemiring P] [MulSemiringAction M P]

variable {Q : Type _} [CommSemiring Q] [MulSemiringAction M Q]

open Polynomial

/- warning: mul_semiring_action_hom.polynomial -> MulSemiringActionHom.polynomial is a dubious translation:
lean 3 declaration is
  forall {M : Type.{u1}} [_inst_1 : Monoid.{u1} M] {P : Type.{u2}} [_inst_2 : CommSemiring.{u2} P] [_inst_3 : MulSemiringAction.{u1, u2} M P _inst_1 (CommSemiring.toSemiring.{u2} P _inst_2)] {Q : Type.{u3}} [_inst_4 : CommSemiring.{u3} Q] [_inst_5 : MulSemiringAction.{u1, u3} M Q _inst_1 (CommSemiring.toSemiring.{u3} Q _inst_4)], (MulSemiringActionHom.{u1, u2, u3} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5) -> (MulSemiringActionHom.{u1, u2, u3} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.mulSemiringAction.{u1, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.semiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.mulSemiringAction.{u1, u3} M _inst_1 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5))
but is expected to have type
  forall {M : Type.{u1}} [_inst_1 : Monoid.{u1} M] {P : Type.{u2}} [_inst_2 : CommSemiring.{u2} P] [_inst_3 : MulSemiringAction.{u1, u2} M P _inst_1 (CommSemiring.toSemiring.{u2} P _inst_2)] {Q : Type.{u3}} [_inst_4 : CommSemiring.{u3} Q] [_inst_5 : MulSemiringAction.{u1, u3} M Q _inst_1 (CommSemiring.toSemiring.{u3} Q _inst_4)], (MulSemiringActionHom.{u1, u2, u3} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5) -> (MulSemiringActionHom.{u1, u2, u3} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u1, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.semiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u1, u3} M _inst_1 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5))
Case conversion may be inaccurate. Consider using '#align mul_semiring_action_hom.polynomial MulSemiringActionHom.polynomialₓ'. -/
/-- An equivariant map induces an equivariant map on polynomials. -/
protected noncomputable def polynomial (g : P →+*[M] Q) : P[X] →+*[M] Q[X]
    where
  toFun := map g
  map_smul' m p :=
    Polynomial.induction_on p
      (fun b => by rw [smul_C, map_C, coe_fn_coe, g.map_smul, map_C, coe_fn_coe, smul_C])
      (fun p q ihp ihq => by
        rw [smul_add, Polynomial.map_add, ihp, ihq, Polynomial.map_add, smul_add])
      fun n b ih => by
      rw [smul_mul', smul_C, smul_pow', smul_X, Polynomial.map_mul, map_C, Polynomial.map_pow,
        map_X, coe_fn_coe, g.map_smul, Polynomial.map_mul, map_C, Polynomial.map_pow, map_X,
        smul_mul', smul_C, smul_pow', smul_X, coe_fn_coe]
  map_zero' := Polynomial.map_zero g
  map_add' p q := Polynomial.map_add g
  map_one' := Polynomial.map_one g
  map_mul' p q := Polynomial.map_mul g
#align mul_semiring_action_hom.polynomial MulSemiringActionHom.polynomial

/- warning: mul_semiring_action_hom.coe_polynomial -> MulSemiringActionHom.coe_polynomial is a dubious translation:
lean 3 declaration is
  forall {M : Type.{u1}} [_inst_1 : Monoid.{u1} M] {P : Type.{u2}} [_inst_2 : CommSemiring.{u2} P] [_inst_3 : MulSemiringAction.{u1, u2} M P _inst_1 (CommSemiring.toSemiring.{u2} P _inst_2)] {Q : Type.{u3}} [_inst_4 : CommSemiring.{u3} Q] [_inst_5 : MulSemiringAction.{u1, u3} M Q _inst_1 (CommSemiring.toSemiring.{u3} Q _inst_4)] (g : MulSemiringActionHom.{u1, u2, u3} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5), Eq.{max (succ u2) (succ u3)} ((fun (_x : MulSemiringActionHom.{u1, u2, u3} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.mulSemiringAction.{u1, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.semiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.mulSemiringAction.{u1, u3} M _inst_1 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5)) => (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) -> (Polynomial.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4))) (MulSemiringActionHom.polynomial.{u1, u2, u3} M _inst_1 P _inst_2 _inst_3 Q _inst_4 _inst_5 g)) (coeFn.{max (succ u2) (succ u3), max (succ u2) (succ u3)} (MulSemiringActionHom.{u1, u2, u3} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.mulSemiringAction.{u1, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.semiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.mulSemiringAction.{u1, u3} M _inst_1 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5)) (fun (_x : MulSemiringActionHom.{u1, u2, u3} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.mulSemiringAction.{u1, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.semiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.mulSemiringAction.{u1, u3} M _inst_1 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5)) => (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) -> (Polynomial.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4))) ([anonymous].{u1, u2, u3} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.mulSemiringAction.{u1, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.semiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (Polynomial.mulSemiringAction.{u1, u3} M _inst_1 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5)) (MulSemiringActionHom.polynomial.{u1, u2, u3} M _inst_1 P _inst_2 _inst_3 Q _inst_4 _inst_5 g)) (Polynomial.map.{u2, u3} P Q (CommSemiring.toSemiring.{u2} P _inst_2) (CommSemiring.toSemiring.{u3} Q _inst_4) ((fun (a : Sort.{max (succ u2) (succ u3)}) (b : Sort.{max (succ u2) (succ u3)}) [self : HasLiftT.{max (succ u2) (succ u3), max (succ u2) (succ u3)} a b] => self.0) (MulSemiringActionHom.{u1, u2, u3} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5) (RingHom.{u2, u3} P Q (Semiring.toNonAssocSemiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Semiring.toNonAssocSemiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4))) (HasLiftT.mk.{max (succ u2) (succ u3), max (succ u2) (succ u3)} (MulSemiringActionHom.{u1, u2, u3} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5) (RingHom.{u2, u3} P Q (Semiring.toNonAssocSemiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Semiring.toNonAssocSemiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4))) (CoeTCₓ.coe.{max (succ u2) (succ u3), max (succ u2) (succ u3)} (MulSemiringActionHom.{u1, u2, u3} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5) (RingHom.{u2, u3} P Q (Semiring.toNonAssocSemiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Semiring.toNonAssocSemiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4))) (RingHom.hasCoeT.{max u2 u3, u2, u3} (MulSemiringActionHom.{u1, u2, u3} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5) P Q (Semiring.toNonAssocSemiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Semiring.toNonAssocSemiring.{u3} Q (CommSemiring.toSemiring.{u3} Q _inst_4)) (MulSemiringActionHomClass.toRingHomClass.{max u2 u3, u1, u2, u3} (MulSemiringActionHom.{u1, u2, u3} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5) M P Q _inst_1 (CommSemiring.toSemiring.{u2} P _inst_2) (CommSemiring.toSemiring.{u3} Q _inst_4) (MulSemiringAction.toDistribMulAction.{u1, u2} M P _inst_1 (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (MulSemiringAction.toDistribMulAction.{u1, u3} M Q _inst_1 (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5) (MulSemiringActionHom.mulSemiringActionHomClass.{u1, u2, u3} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u3} Q _inst_4) _inst_5))))) g))
but is expected to have type
  forall {M : Type.{u3}} [_inst_1 : Monoid.{u3} M] {P : Type.{u2}} [_inst_2 : CommSemiring.{u2} P] [_inst_3 : MulSemiringAction.{u3, u2} M P _inst_1 (CommSemiring.toSemiring.{u2} P _inst_2)] {Q : Type.{u1}} [_inst_4 : CommSemiring.{u1} Q] [_inst_5 : MulSemiringAction.{u3, u1} M Q _inst_1 (CommSemiring.toSemiring.{u1} Q _inst_4)] (g : MulSemiringActionHom.{u3, u2, u1} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5), Eq.{max (succ u2) (succ u1)} (forall (a : Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)), (fun (x._@.Mathlib.Algebra.Hom.GroupAction._hyg.2186 : Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) => Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) a) (FunLike.coe.{max (succ u2) (succ u1), succ u2, succ u1} (MulSemiringActionHom.{u3, u2, u1} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u1} M _inst_1 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5)) (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (fun (_x : Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) => (fun (x._@.Mathlib.Algebra.Hom.GroupAction._hyg.2186 : Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) => Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) _x) (SMulHomClass.toFunLike.{max u2 u1, u3, u2, u1} (MulSemiringActionHom.{u3, u2, u1} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u1} M _inst_1 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5)) M (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (SMulZeroClass.toSMul.{u3, u2} M (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (AddMonoid.toZero.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (AddMonoidWithOne.toAddMonoid.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (NonAssocSemiring.toAddCommMonoidWithOne.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Semiring.toNonAssocSemiring.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2))))))) (DistribSMul.toSMulZeroClass.{u3, u2} M (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (AddMonoid.toAddZeroClass.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (AddMonoidWithOne.toAddMonoid.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (NonAssocSemiring.toAddCommMonoidWithOne.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Semiring.toNonAssocSemiring.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2))))))) (DistribMulAction.toDistribSMul.{u3, u2} M (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (NonAssocSemiring.toAddCommMonoidWithOne.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Semiring.toNonAssocSemiring.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)))))) (MulSemiringAction.toDistribMulAction.{u3, u2} M (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) _inst_1 (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3))))) (SMulZeroClass.toSMul.{u3, u1} M (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (AddMonoid.toZero.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (AddMonoidWithOne.toAddMonoid.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (NonAssocSemiring.toAddCommMonoidWithOne.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Semiring.toNonAssocSemiring.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4))))))) (DistribSMul.toSMulZeroClass.{u3, u1} M (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (AddMonoid.toAddZeroClass.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (AddMonoidWithOne.toAddMonoid.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (NonAssocSemiring.toAddCommMonoidWithOne.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Semiring.toNonAssocSemiring.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4))))))) (DistribMulAction.toDistribSMul.{u3, u1} M (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) _inst_1 (AddMonoidWithOne.toAddMonoid.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (NonAssocSemiring.toAddCommMonoidWithOne.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Semiring.toNonAssocSemiring.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)))))) (MulSemiringAction.toDistribMulAction.{u3, u1} M (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) _inst_1 (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u1} M _inst_1 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5))))) (DistribMulActionHomClass.toSMulHomClass.{max u2 u1, u3, u2, u1} (MulSemiringActionHom.{u3, u2, u1} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u1} M _inst_1 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5)) M (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) _inst_1 (AddMonoidWithOne.toAddMonoid.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (AddCommMonoidWithOne.toAddMonoidWithOne.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (NonAssocSemiring.toAddCommMonoidWithOne.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Semiring.toNonAssocSemiring.{u2} (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)))))) (AddMonoidWithOne.toAddMonoid.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (AddCommMonoidWithOne.toAddMonoidWithOne.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (NonAssocSemiring.toAddCommMonoidWithOne.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Semiring.toNonAssocSemiring.{u1} (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)))))) (MulSemiringAction.toDistribMulAction.{u3, u2} M (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) _inst_1 (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3)) (MulSemiringAction.toDistribMulAction.{u3, u1} M (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) _inst_1 (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u1} M _inst_1 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5)) (MulSemiringActionHomClass.toDistribMulActionHomClass.{max u2 u1, u3, u2, u1} (MulSemiringActionHom.{u3, u2, u1} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u1} M _inst_1 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5)) M (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) _inst_1 (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (MulSemiringAction.toDistribMulAction.{u3, u2} M (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) _inst_1 (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3)) (MulSemiringAction.toDistribMulAction.{u3, u1} M (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) _inst_1 (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u1} M _inst_1 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5)) (MulSemiringActionHom.instMulSemiringActionHomClassMulSemiringActionHomToDistribMulActionToDistribMulAction.{u3, u2, u1} M _inst_1 (Polynomial.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.semiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u2} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (Polynomial.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.semiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (Polynomial.instMulSemiringActionPolynomialSemiring.{u3, u1} M _inst_1 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5))))) (MulSemiringActionHom.polynomial.{u3, u2, u1} M _inst_1 P _inst_2 _inst_3 Q _inst_4 _inst_5 g)) (Polynomial.map.{u2, u1} P Q (CommSemiring.toSemiring.{u2} P _inst_2) (CommSemiring.toSemiring.{u1} Q _inst_4) (RingHomClass.toRingHom.{max u2 u1, u2, u1} (MulSemiringActionHom.{u3, u2, u1} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5) P Q (Semiring.toNonAssocSemiring.{u2} P (CommSemiring.toSemiring.{u2} P _inst_2)) (Semiring.toNonAssocSemiring.{u1} Q (CommSemiring.toSemiring.{u1} Q _inst_4)) (MulSemiringActionHomClass.toRingHomClass.{max u2 u1, u3, u2, u1} (MulSemiringActionHom.{u3, u2, u1} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5) M P Q _inst_1 (CommSemiring.toSemiring.{u2} P _inst_2) (CommSemiring.toSemiring.{u1} Q _inst_4) (MulSemiringAction.toDistribMulAction.{u3, u2} M P _inst_1 (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3) (MulSemiringAction.toDistribMulAction.{u3, u1} M Q _inst_1 (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5) (MulSemiringActionHom.instMulSemiringActionHomClassMulSemiringActionHomToDistribMulActionToDistribMulAction.{u3, u2, u1} M _inst_1 P (CommSemiring.toSemiring.{u2} P _inst_2) _inst_3 Q (CommSemiring.toSemiring.{u1} Q _inst_4) _inst_5)) g))
Case conversion may be inaccurate. Consider using '#align mul_semiring_action_hom.coe_polynomial MulSemiringActionHom.coe_polynomialₓ'. -/
@[simp]
theorem coe_polynomial (g : P →+*[M] Q) : (g.Polynomial : P[X] → Q[X]) = map g :=
  rfl
#align mul_semiring_action_hom.coe_polynomial MulSemiringActionHom.coe_polynomial

end MulSemiringActionHom