l3lab/ntp-mathlib huggingface dataset:
/-- A linear equivalence of two modules restricts to a linear equivalence from any submodule
`p` of the domain onto the image of that submodule.

This is the linear version of `AddEquiv.submonoidMap` and `AddEquiv.subgroupMap`.

This is `LinearEquiv.ofSubmodule'` but with `map` on the right instead of `comap` on the left. -/
def submoduleMap (p : Submodule R M) : p ≃ₛₗ[σ₁₂] ↥(p.map (e : M →ₛₗ[σ₁₂] M₂) : Submodule R₂ M₂) :=
  { ((e : M →ₛₗ[σ₁₂] M₂).domRestrict p).codRestrict (p.map (e : M →ₛₗ[σ₁₂] M₂)) fun x =>
      ⟨x, by
        simp only [LinearMap.domRestrict_apply, eq_self_iff_true, and_true_iff, SetLike.coe_mem,
          SetLike.mem_coe]⟩ with
    invFun := fun y =>
      ⟨(e.symm : M₂ →ₛₗ[σ₂₁] M) y, by
        rcases y with ⟨y', hy⟩
        rw [Submodule.mem_map] at hy
        rcases hy with ⟨x, hx, hxy⟩
        subst hxy
        simp only [symm_apply_apply, Submodule.coe_mk, coe_coe, hx]⟩
    left_inv := fun x => by
      

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁷ : Semiring R
inst✝⁶ : Semiring R₂
inst✝⁵ : Semiring R₃
inst✝⁴ : Semiring R₄
inst✝³ : AddCommMonoid M
inst✝² : AddCommMonoid M₂
inst✝¹ : AddCommMonoid M₃
inst✝ : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
e e' : M ≃ₛₗ[σ₁₂] M₂
p : Submodule R M
src✝ : ↥p →ₛₗ[σ₁₂] ↥(Submodule.map (↑e) p) :=
  LinearMap.codRestrict (Submodule.map (↑e) p) (LinearMap.domRestrict (↑e) p)
    (_ : ∀ (x : ↥p), ∃ a ∈ ↑p, ↑e a = (LinearMap.domRestrict (↑e) p) x)
x : ↥p
⊢ (fun y => { val := ↑(symm e) ↑y, property := (_ : ↑(symm e) ↑y ∈ p) })
      (AddHom.toFun
        { toAddHom := src✝.toAddHom,
            map_smul' :=
              (_ :
                ∀ (r : R) (x : ↥p),
                  AddHom.toFun src✝.toAddHom (r • x) = σ₁₂ r • AddHom.toFun src✝.toAddHom x) }.toAddHom
        x) =
    x

Next tactic:
simp only [LinearMap.domRestrict_apply, LinearMap.codRestrict_apply, LinearMap.toFun_eq_coe,
        LinearEquiv.coe_coe, LinearEquiv.symm_apply_apply, SetLike.eta]
/-- A linear equivalence of two modules restricts to a linear equivalence from any submodule
`p` of the domain onto the image of that submodule.

This is the linear version of `AddEquiv.submonoidMap` and `AddEquiv.subgroupMap`.

This is `LinearEquiv.ofSubmodule'` but with `map` on the right instead of `comap` on the left. -/
def submoduleMap (p : Submodule R M) : p ≃ₛₗ[σ₁₂] ↥(p.map (e : M →ₛₗ[σ₁₂] M₂) : Submodule R₂ M₂) :=
  { ((e : M →ₛₗ[σ₁₂] M₂).domRestrict p).codRestrict (p.map (e : M →ₛₗ[σ₁₂] M₂)) fun x =>
      ⟨x, by
        simp only [LinearMap.domRestrict_apply, eq_self_iff_true, and_true_iff, SetLike.coe_mem,
          SetLike.mem_coe]⟩ with
    invFun := fun y =>
      ⟨(e.symm : M₂ →ₛₗ[σ₂₁] M) y, by
        rcases y with ⟨y', hy⟩
        rw [Submodule.mem_map] at hy
        rcases hy with ⟨x, hx, hxy⟩
        subst hxy
        simp only [symm_apply_apply, Submodule.coe_mk, coe_coe, hx]⟩
    left_inv := fun x => by
      simp only [LinearMap.domRestrict_apply, LinearMap.codRestrict_apply, LinearMap.toFun_eq_coe,
        LinearEquiv.coe_coe, LinearEquiv.symm_apply_apply, SetLike.eta]
    right_inv := fun y => by
      

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁷ : Semiring R
inst✝⁶ : Semiring R₂
inst✝⁵ : Semiring R₃
inst✝⁴ : Semiring R₄
inst✝³ : AddCommMonoid M
inst✝² : AddCommMonoid M₂
inst✝¹ : AddCommMonoid M₃
inst✝ : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
e e' : M ≃ₛₗ[σ₁₂] M₂
p : Submodule R M
src✝ : ↥p →ₛₗ[σ₁₂] ↥(Submodule.map (↑e) p) :=
  LinearMap.codRestrict (Submodule.map (↑e) p) (LinearMap.domRestrict (↑e) p)
    (_ : ∀ (x : ↥p), ∃ a ∈ ↑p, ↑e a = (LinearMap.domRestrict (↑e) p) x)
y : ↥(Submodule.map (↑e) p)
⊢ AddHom.toFun
      { toAddHom := src✝.toAddHom,
          map_smul' :=
            (_ :
              ∀ (r : R) (x : ↥p), AddHom.toFun src✝.toAddHom (r • x) = σ₁₂ r • AddHom.toFun src✝.toAddHom x) }.toAddHom
      ((fun y => { val := ↑(symm e) ↑y, property := (_ : ↑(symm e) ↑y ∈ p) }) y) =
    y

Next tactic:
apply SetCoe.ext
/-- A linear equivalence of two modules restricts to a linear equivalence from any submodule
`p` of the domain onto the image of that submodule.

This is the linear version of `AddEquiv.submonoidMap` and `AddEquiv.subgroupMap`.

This is `LinearEquiv.ofSubmodule'` but with `map` on the right instead of `comap` on the left. -/
def submoduleMap (p : Submodule R M) : p ≃ₛₗ[σ₁₂] ↥(p.map (e : M →ₛₗ[σ₁₂] M₂) : Submodule R₂ M₂) :=
  { ((e : M →ₛₗ[σ₁₂] M₂).domRestrict p).codRestrict (p.map (e : M →ₛₗ[σ₁₂] M₂)) fun x =>
      ⟨x, by
        simp only [LinearMap.domRestrict_apply, eq_self_iff_true, and_true_iff, SetLike.coe_mem,
          SetLike.mem_coe]⟩ with
    invFun := fun y =>
      ⟨(e.symm : M₂ →ₛₗ[σ₂₁] M) y, by
        rcases y with ⟨y', hy⟩
        rw [Submodule.mem_map] at hy
        rcases hy with ⟨x, hx, hxy⟩
        subst hxy
        simp only [symm_apply_apply, Submodule.coe_mk, coe_coe, hx]⟩
    left_inv := fun x => by
      simp only [LinearMap.domRestrict_apply, LinearMap.codRestrict_apply, LinearMap.toFun_eq_coe,
        LinearEquiv.coe_coe, LinearEquiv.symm_apply_apply, SetLike.eta]
    right_inv := fun y => by
      apply SetCoe.ext
      

Proof state:
case a
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁷ : Semiring R
inst✝⁶ : Semiring R₂
inst✝⁵ : Semiring R₃
inst✝⁴ : Semiring R₄
inst✝³ : AddCommMonoid M
inst✝² : AddCommMonoid M₂
inst✝¹ : AddCommMonoid M₃
inst✝ : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
e e' : M ≃ₛₗ[σ₁₂] M₂
p : Submodule R M
src✝ : ↥p →ₛₗ[σ₁₂] ↥(Submodule.map (↑e) p) :=
  LinearMap.codRestrict (Submodule.map (↑e) p) (LinearMap.domRestrict (↑e) p)
    (_ : ∀ (x : ↥p), ∃ a ∈ ↑p, ↑e a = (LinearMap.domRestrict (↑e) p) x)
y : ↥(Submodule.map (↑e) p)
⊢ ↑(AddHom.toFun
        { toAddHom := src✝.toAddHom,
            map_smul' :=
              (_ :
                ∀ (r : R) (x : ↥p),
                  AddHom.toFun src✝.toAddHom (r • x) = σ₁₂ r • AddHom.toFun src✝.toAddHom x) }.toAddHom
        ((fun y => { val := ↑(symm e) ↑y, property := (_ : ↑(symm e) ↑y ∈ p) }) y)) =
    ↑y

Next tactic:
simp only [LinearMap.domRestrict_apply, LinearMap.codRestrict_apply, LinearMap.toFun_eq_coe,
        LinearEquiv.coe_coe, LinearEquiv.apply_symm_apply]
/-- Linear equivalence between a curried and uncurried function.
  Differs from `TensorProduct.curry`. -/
protected def curry : (V × V₂ → R) ≃ₗ[R] V → V₂ → R :=
  { Equiv.curry _ _ _ with
    map_add' := fun _ _ => by
      

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁷ : Semiring R
inst✝⁶ : Semiring R₂
inst✝⁵ : Semiring R₃
inst✝⁴ : Semiring R₄
inst✝³ : AddCommMonoid M
inst✝² : AddCommMonoid M₂
inst✝¹ : AddCommMonoid M₃
inst✝ : AddCommMonoid M₄
src✝ : (V × V₂ → R) ≃ (V → V₂ → R) := Equiv.curry V V₂ R
x✝¹ x✝ : V × V₂ → R
⊢ Equiv.toFun src✝ (x✝¹ + x✝) = Equiv.toFun src✝ x✝¹ + Equiv.toFun src✝ x✝

Next tactic:
ext
/-- Linear equivalence between a curried and uncurried function.
  Differs from `TensorProduct.curry`. -/
protected def curry : (V × V₂ → R) ≃ₗ[R] V → V₂ → R :=
  { Equiv.curry _ _ _ with
    map_add' := fun _ _ => by
      ext
      

Proof state:
case h.h
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁷ : Semiring R
inst✝⁶ : Semiring R₂
inst✝⁵ : Semiring R₃
inst✝⁴ : Semiring R₄
inst✝³ : AddCommMonoid M
inst✝² : AddCommMonoid M₂
inst✝¹ : AddCommMonoid M₃
inst✝ : AddCommMonoid M₄
src✝ : (V × V₂ → R) ≃ (V → V₂ → R) := Equiv.curry V V₂ R
x✝³ x✝² : V × V₂ → R
x✝¹ : V
x✝ : V₂
⊢ Equiv.toFun src✝ (x✝³ + x✝²) x✝¹ x✝ = (Equiv.toFun src✝ x✝³ + Equiv.toFun src✝ x✝²) x✝¹ x✝

Next tactic:
rfl
/-- Linear equivalence between a curried and uncurried function.
  Differs from `TensorProduct.curry`. -/
protected def curry : (V × V₂ → R) ≃ₗ[R] V → V₂ → R :=
  { Equiv.curry _ _ _ with
    map_add' := fun _ _ => by
      ext
      rfl
    map_smul' := fun _ _ => by
      

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁷ : Semiring R
inst✝⁶ : Semiring R₂
inst✝⁵ : Semiring R₃
inst✝⁴ : Semiring R₄
inst✝³ : AddCommMonoid M
inst✝² : AddCommMonoid M₂
inst✝¹ : AddCommMonoid M₃
inst✝ : AddCommMonoid M₄
src✝ : (V × V₂ → R) ≃ (V → V₂ → R) := Equiv.curry V V₂ R
x✝¹ : R
x✝ : V × V₂ → R
⊢ AddHom.toFun
      { toFun := src✝.toFun,
        map_add' :=
          (_ : ∀ (x x_1 : V × V₂ → R), Equiv.toFun src✝ (x + x_1) = Equiv.toFun src✝ x + Equiv.toFun src✝ x_1) }
      (x✝¹ • x✝) =
    (RingHom.id R) x✝¹ •
      AddHom.toFun
        { toFun := src✝.toFun,
          map_add' :=
            (_ : ∀ (x x_1 : V × V₂ → R), Equiv.toFun src✝ (x + x_1) = Equiv.toFun src✝ x + Equiv.toFun src✝ x_1) }
        x✝

Next tactic:
ext
/-- Linear equivalence between a curried and uncurried function.
  Differs from `TensorProduct.curry`. -/
protected def curry : (V × V₂ → R) ≃ₗ[R] V → V₂ → R :=
  { Equiv.curry _ _ _ with
    map_add' := fun _ _ => by
      ext
      rfl
    map_smul' := fun _ _ => by
      ext
      

Proof state:
case h.h
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁷ : Semiring R
inst✝⁶ : Semiring R₂
inst✝⁵ : Semiring R₃
inst✝⁴ : Semiring R₄
inst✝³ : AddCommMonoid M
inst✝² : AddCommMonoid M₂
inst✝¹ : AddCommMonoid M₃
inst✝ : AddCommMonoid M₄
src✝ : (V × V₂ → R) ≃ (V → V₂ → R) := Equiv.curry V V₂ R
x✝³ : R
x✝² : V × V₂ → R
x✝¹ : V
x✝ : V₂
⊢ AddHom.toFun
      { toFun := src✝.toFun,
        map_add' :=
          (_ : ∀ (x x_1 : V × V₂ → R), Equiv.toFun src✝ (x + x_1) = Equiv.toFun src✝ x + Equiv.toFun src✝ x_1) }
      (x✝³ • x✝²) x✝¹ x✝ =
    ((RingHom.id R) x✝³ •
        AddHom.toFun
          { toFun := src✝.toFun,
            map_add' :=
              (_ : ∀ (x x_1 : V × V₂ → R), Equiv.toFun src✝ (x + x_1) = Equiv.toFun src✝ x + Equiv.toFun src✝ x_1) }
          x✝²)
      x✝¹ x✝

Next tactic:
rfl
@[simp]
theorem ofEq_rfl : ofEq p p rfl = LinearEquiv.refl R p := by 

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁸ : Semiring R
inst✝⁷ : Semiring R₂
inst✝⁶ : Semiring R₃
inst✝⁵ : Semiring R₄
inst✝⁴ : AddCommMonoid M
inst✝³ : AddCommMonoid M₂
inst✝² : AddCommMonoid M₃
inst✝¹ : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
module_M₃ : Module R₃ M₃
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
σ₂₃ : R₂ →+* R₃
σ₁₃ : R →+* R₃
inst✝ : RingHomCompTriple σ₁₂ σ₂₃ σ₁₃
σ₃₂ : R₃ →+* R₂
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
re₂₃ : RingHomInvPair σ₂₃ σ₃₂
re₃₂ : RingHomInvPair σ₃₂ σ₂₃
f : M →ₛₗ[σ₁₂] M₂
g : M₂ →ₛₗ[σ₂₁] M
e : M ≃ₛₗ[σ₁₂] M₂
h : M₂ →ₛₗ[σ₂₃] M₃
e'' : M₂ ≃ₛₗ[σ₂₃] M₃
p q : Submodule R M
⊢ ofEq p p (_ : p = p) = refl R ↥p

Next tactic:
ext
@[simp]
theorem ofEq_rfl : ofEq p p rfl = LinearEquiv.refl R p := by ext; 

Proof state:
case h.a
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁸ : Semiring R
inst✝⁷ : Semiring R₂
inst✝⁶ : Semiring R₃
inst✝⁵ : Semiring R₄
inst✝⁴ : AddCommMonoid M
inst✝³ : AddCommMonoid M₂
inst✝² : AddCommMonoid M₃
inst✝¹ : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
module_M₃ : Module R₃ M₃
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
σ₂₃ : R₂ →+* R₃
σ₁₃ : R →+* R₃
inst✝ : RingHomCompTriple σ₁₂ σ₂₃ σ₁₃
σ₃₂ : R₃ →+* R₂
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
re₂₃ : RingHomInvPair σ₂₃ σ₃₂
re₃₂ : RingHomInvPair σ₃₂ σ₂₃
f : M →ₛₗ[σ₁₂] M₂
g : M₂ →ₛₗ[σ₂₁] M
e : M ≃ₛₗ[σ₁₂] M₂
h : M₂ →ₛₗ[σ₂₃] M₃
e'' : M₂ ≃ₛₗ[σ₂₃] M₃
p q : Submodule R M
x✝ : ↥p
⊢ ↑((ofEq p p (_ : p = p)) x✝) = ↑((refl R ↥p) x✝)

Next tactic:
rfl
theorem ofSubmodule'_toLinearMap [Module R M] [Module R₂ M₂] (f : M ≃ₛₗ[σ₁₂] M₂)
    (U : Submodule R₂ M₂) :
    (f.ofSubmodule' U).toLinearMap = (f.toLinearMap.domRestrict _).codRestrict _ Subtype.prop := by
  

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝¹⁰ : Semiring R
inst✝⁹ : Semiring R₂
inst✝⁸ : Semiring R₃
inst✝⁷ : Semiring R₄
inst✝⁶ : AddCommMonoid M
inst✝⁵ : AddCommMonoid M₂
inst✝⁴ : AddCommMonoid M₃
inst✝³ : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
module_M₃ : Module R₃ M₃
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
σ₂₃ : R₂ →+* R₃
σ₁₃ : R →+* R₃
inst✝² : RingHomCompTriple σ₁₂ σ₂₃ σ₁₃
σ₃₂ : R₃ →+* R₂
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
re₂₃ : RingHomInvPair σ₂₃ σ₃₂
re₃₂ : RingHomInvPair σ₃₂ σ₂₃
f✝ : M →ₛₗ[σ₁₂] M₂
g : M₂ →ₛₗ[σ₂₁] M
e : M ≃ₛₗ[σ₁₂] M₂
h : M₂ →ₛₗ[σ₂₃] M₃
e'' : M₂ ≃ₛₗ[σ₂₃] M₃
p q : Submodule R M
inst✝¹ : Module R M
inst✝ : Module R₂ M₂
f : M ≃ₛₗ[σ₁₂] M₂
U : Submodule R₂ M₂
⊢ ↑(ofSubmodule' f U) =
    LinearMap.codRestrict U (LinearMap.domRestrict (↑f) (Submodule.comap (↑f) U))
      (_ : ∀ (x : ↥(Submodule.comap (↑f) U)), ↑x ∈ Submodule.comap (↑f) U)

Next tactic:
ext
theorem ofSubmodule'_toLinearMap [Module R M] [Module R₂ M₂] (f : M ≃ₛₗ[σ₁₂] M₂)
    (U : Submodule R₂ M₂) :
    (f.ofSubmodule' U).toLinearMap = (f.toLinearMap.domRestrict _).codRestrict _ Subtype.prop := by
  ext
  

Proof state:
case h.a
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝¹⁰ : Semiring R
inst✝⁹ : Semiring R₂
inst✝⁸ : Semiring R₃
inst✝⁷ : Semiring R₄
inst✝⁶ : AddCommMonoid M
inst✝⁵ : AddCommMonoid M₂
inst✝⁴ : AddCommMonoid M₃
inst✝³ : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
module_M₃ : Module R₃ M₃
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
σ₂₃ : R₂ →+* R₃
σ₁₃ : R →+* R₃
inst✝² : RingHomCompTriple σ₁₂ σ₂₃ σ₁₃
σ₃₂ : R₃ →+* R₂
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
re₂₃ : RingHomInvPair σ₂₃ σ₃₂
re₃₂ : RingHomInvPair σ₃₂ σ₂₃
f✝ : M →ₛₗ[σ₁₂] M₂
g : M₂ →ₛₗ[σ₂₁] M
e : M ≃ₛₗ[σ₁₂] M₂
h : M₂ →ₛₗ[σ₂₃] M₃
e'' : M₂ ≃ₛₗ[σ₂₃] M₃
p q : Submodule R M
inst✝¹ : Module R M
inst✝ : Module R₂ M₂
f : M ≃ₛₗ[σ₁₂] M₂
U : Submodule R₂ M₂
x✝ : ↥(Submodule.comap (↑f) U)
⊢ ↑(↑(ofSubmodule' f U) x✝) =
    ↑((LinearMap.codRestrict U (LinearMap.domRestrict (↑f) (Submodule.comap (↑f) U))
          (_ : ∀ (x : ↥(Submodule.comap (↑f) U)), ↑x ∈ Submodule.comap (↑f) U))
        x✝)

Next tactic:
rfl
theorem eq_bot_of_equiv [Module R₂ M₂] (e : p ≃ₛₗ[σ₁₂] (⊥ : Submodule R₂ M₂)) : p = ⊥ := by
  

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁹ : Semiring R
inst✝⁸ : Semiring R₂
inst✝⁷ : Semiring R₃
inst✝⁶ : Semiring R₄
inst✝⁵ : AddCommMonoid M
inst✝⁴ : AddCommMonoid M₂
inst✝³ : AddCommMonoid M₃
inst✝² : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
module_M₃ : Module R₃ M₃
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
σ₂₃ : R₂ →+* R₃
σ₁₃ : R →+* R₃
inst✝¹ : RingHomCompTriple σ₁₂ σ₂₃ σ₁₃
σ₃₂ : R₃ →+* R₂
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
re₂₃ : RingHomInvPair σ₂₃ σ₃₂
re₃₂ : RingHomInvPair σ₃₂ σ₂₃
f : M →ₛₗ[σ₁₂] M₂
g : M₂ →ₛₗ[σ₂₁] M
e✝ : M ≃ₛₗ[σ₁₂] M₂
h : M₂ →ₛₗ[σ₂₃] M₃
e'' : M₂ ≃ₛₗ[σ₂₃] M₃
p q : Submodule R M
inst✝ : Module R₂ M₂
e : ↥p ≃ₛₗ[σ₁₂] ↥⊥
⊢ p = ⊥

Next tactic:
refine' bot_unique (SetLike.le_def.2 fun b hb => (Submodule.mem_bot R).2 _)
theorem eq_bot_of_equiv [Module R₂ M₂] (e : p ≃ₛₗ[σ₁₂] (⊥ : Submodule R₂ M₂)) : p = ⊥ := by
  refine' bot_unique (SetLike.le_def.2 fun b hb => (Submodule.mem_bot R).2 _)
  

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁹ : Semiring R
inst✝⁸ : Semiring R₂
inst✝⁷ : Semiring R₃
inst✝⁶ : Semiring R₄
inst✝⁵ : AddCommMonoid M
inst✝⁴ : AddCommMonoid M₂
inst✝³ : AddCommMonoid M₃
inst✝² : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
module_M₃ : Module R₃ M₃
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
σ₂₃ : R₂ →+* R₃
σ₁₃ : R →+* R₃
inst✝¹ : RingHomCompTriple σ₁₂ σ₂₃ σ₁₃
σ₃₂ : R₃ →+* R₂
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
re₂₃ : RingHomInvPair σ₂₃ σ₃₂
re₃₂ : RingHomInvPair σ₃₂ σ₂₃
f : M →ₛₗ[σ₁₂] M₂
g : M₂ →ₛₗ[σ₂₁] M
e✝ : M ≃ₛₗ[σ₁₂] M₂
h : M₂ →ₛₗ[σ₂₃] M₃
e'' : M₂ ≃ₛₗ[σ₂₃] M₃
p q : Submodule R M
inst✝ : Module R₂ M₂
e : ↥p ≃ₛₗ[σ₁₂] ↥⊥
b : M
hb : b ∈ p
⊢ b = 0

Next tactic:
rw [← p.mk_eq_zero hb, ← e.map_eq_zero_iff]
theorem eq_bot_of_equiv [Module R₂ M₂] (e : p ≃ₛₗ[σ₁₂] (⊥ : Submodule R₂ M₂)) : p = ⊥ := by
  refine' bot_unique (SetLike.le_def.2 fun b hb => (Submodule.mem_bot R).2 _)
  rw [← p.mk_eq_zero hb, ← e.map_eq_zero_iff]
  

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝⁹ : Semiring R
inst✝⁸ : Semiring R₂
inst✝⁷ : Semiring R₃
inst✝⁶ : Semiring R₄
inst✝⁵ : AddCommMonoid M
inst✝⁴ : AddCommMonoid M₂
inst✝³ : AddCommMonoid M₃
inst✝² : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
module_M₃ : Module R₃ M₃
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
σ₂₃ : R₂ →+* R₃
σ₁₃ : R →+* R₃
inst✝¹ : RingHomCompTriple σ₁₂ σ₂₃ σ₁₃
σ₃₂ : R₃ →+* R₂
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
re₂₃ : RingHomInvPair σ₂₃ σ₃₂
re₃₂ : RingHomInvPair σ₃₂ σ₂₃
f : M →ₛₗ[σ₁₂] M₂
g : M₂ →ₛₗ[σ₂₁] M
e✝ : M ≃ₛₗ[σ₁₂] M₂
h : M₂ →ₛₗ[σ₂₃] M₃
e'' : M₂ ≃ₛₗ[σ₂₃] M₃
p q : Submodule R M
inst✝ : Module R₂ M₂
e : ↥p ≃ₛₗ[σ₁₂] ↥⊥
b : M
hb : b ∈ p
⊢ e { val := b, property := hb } = 0

Next tactic:
apply Submodule.eq_zero_of_bot_submodule
/-- A linear map `f : M →ₗ[R] M₂` with a left-inverse `g : M₂ →ₗ[R] M` defines a linear
equivalence between `M` and `f.range`.

This is a computable alternative to `LinearEquiv.ofInjective`, and a bidirectional version of
`LinearMap.rangeRestrict`. -/
def ofLeftInverse [RingHomInvPair σ₁₂ σ₂₁] [RingHomInvPair σ₂₁ σ₁₂] {g : M₂ → M}
    (h : Function.LeftInverse g f) : M ≃ₛₗ[σ₁₂] (LinearMap.range f) :=
  { LinearMap.rangeRestrict f with
    toFun := LinearMap.rangeRestrict f
    invFun := g ∘ (LinearMap.range f).subtype
    left_inv := h
    right_inv := fun x =>
      Subtype.ext <|
        let ⟨x', hx'⟩ := LinearMap.mem_range.mp x.prop
        show f (g x) = x by 

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝¹⁰ : Semiring R
inst✝⁹ : Semiring R₂
inst✝⁸ : Semiring R₃
inst✝⁷ : Semiring R₄
inst✝⁶ : AddCommMonoid M
inst✝⁵ : AddCommMonoid M₂
inst✝⁴ : AddCommMonoid M₃
inst✝³ : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
module_M₃ : Module R₃ M₃
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
σ₂₃ : R₂ →+* R₃
σ₁₃ : R →+* R₃
inst✝² : RingHomCompTriple σ₁₂ σ₂₃ σ₁₃
σ₃₂ : R₃ →+* R₂
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
re₂₃ : RingHomInvPair σ₂₃ σ₃₂
re₃₂ : RingHomInvPair σ₃₂ σ₂₃
f : M →ₛₗ[σ₁₂] M₂
g✝ : M₂ →ₛₗ[σ₂₁] M
e : M ≃ₛₗ[σ₁₂] M₂
h✝ : M₂ →ₛₗ[σ₂₃] M₃
e'' : M₂ ≃ₛₗ[σ₂₃] M₃
p q : Submodule R M
inst✝¹ : RingHomInvPair σ₁₂ σ₂₁
inst✝ : RingHomInvPair σ₂₁ σ₁₂
g : M₂ → M
h : LeftInverse g ⇑f
src✝ : M →ₛₗ[σ₁₂] ↥(LinearMap.range f) := LinearMap.rangeRestrict f
x : ↥(LinearMap.range f)
x' : M
hx' : f x' = ↑x
⊢ f (g ↑x) = ↑x

Next tactic:
rw [← hx', h x']
@[simp]
theorem ofBijective_symm_apply_apply [RingHomInvPair σ₁₂ σ₂₁] [RingHomInvPair σ₂₁ σ₁₂] {h} (x : M) :
    (ofBijective f h).symm (f x) = x := by
  

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝¹⁰ : Semiring R
inst✝⁹ : Semiring R₂
inst✝⁸ : Semiring R₃
inst✝⁷ : Semiring R₄
inst✝⁶ : AddCommMonoid M
inst✝⁵ : AddCommMonoid M₂
inst✝⁴ : AddCommMonoid M₃
inst✝³ : AddCommMonoid M₄
module_M : Module R M
module_M₂ : Module R₂ M₂
module_M₃ : Module R₃ M₃
σ₁₂ : R →+* R₂
σ₂₁ : R₂ →+* R
σ₂₃ : R₂ →+* R₃
σ₁₃ : R →+* R₃
inst✝² : RingHomCompTriple σ₁₂ σ₂₃ σ₁₃
σ₃₂ : R₃ →+* R₂
re₁₂ : RingHomInvPair σ₁₂ σ₂₁
re₂₁ : RingHomInvPair σ₂₁ σ₁₂
re₂₃ : RingHomInvPair σ₂₃ σ₃₂
re₃₂ : RingHomInvPair σ₃₂ σ₂₃
f : M →ₛₗ[σ₁₂] M₂
g : M₂ →ₛₗ[σ₂₁] M
e : M ≃ₛₗ[σ₁₂] M₂
h✝ : M₂ →ₛₗ[σ₂₃] M₃
e'' : M₂ ≃ₛₗ[σ₂₃] M₃
p q : Submodule R M
inst✝¹ : RingHomInvPair σ₁₂ σ₂₁
inst✝ : RingHomInvPair σ₂₁ σ₁₂
h : Bijective ⇑f
x : M
⊢ (symm (ofBijective f h)) (f x) = x

Next tactic:
simp [LinearEquiv.symm_apply_eq]
theorem neg_apply (x : M) : neg R x = -x := by 

Proof state:
R : Type u_1
R₁ : Type u_2
R₂ : Type u_3
R₃ : Type u_4
R₄ : Type u_5
S : Type u_6
K : Type u_7
K₂ : Type u_8
M : Type u_9
M' : Type u_10
M₁ : Type u_11
M₂ : Type u_12
M₃ : Type u_13
M₄ : Type u_14
N : Type u_15
N₂ : Type u_16
ι : Type u_17
V : Type u_18
V₂ : Type u_19
inst✝² : Semiring R
inst✝¹ : AddCommGroup M
inst✝ : Module R M
x : M
⊢ (neg R) x = -x

Next tactic:
simp