l3lab/ntp-mathlib huggingface dataset:
/-- Linear maps `(n → R) →ₗ[R] (m → R)` are linearly equivalent to `Matrix m n R`. -/
def LinearMap.toMatrix' : ((n → R) →ₗ[R] m → R) ≃ₗ[R] Matrix m n R where
  toFun f := of fun i j => f (stdBasis R (fun _ => R) j 1) i
  invFun := Matrix.mulVecLin
  right_inv M := by
    ext i j
    simp only [Matrix.mulVec_stdBasis, Matrix.mulVecLin_apply, of_apply]
  left_inv f := by
    

Proof state:
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
⊢ mulVecLin
      (AddHom.toFun
        {
            toAddHom :=
              { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                map_add' :=
                  (_ :
                    ∀ (f g : (n → R) →ₗ[R] m → R),
                      (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                        (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                          (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) },
            map_smul' :=
              (_ :
                ∀ (c : R) (f : (n → R) →ₗ[R] m → R),
                  AddHom.toFun
                      { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                        map_add' :=
                          (_ :
                            ∀ (f g : (n → R) →ₗ[R] m → R),
                              (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                  (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                      (c • f) =
                    (RingHom.id R) c •
                      AddHom.toFun
                        { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                          map_add' :=
                            (_ :
                              ∀ (f g : (n → R) →ₗ[R] m → R),
                                (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                  (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                    (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                        f) }.toAddHom
        f) =
    f

Next tactic:
apply (Pi.basisFun R n).ext
/-- Linear maps `(n → R) →ₗ[R] (m → R)` are linearly equivalent to `Matrix m n R`. -/
def LinearMap.toMatrix' : ((n → R) →ₗ[R] m → R) ≃ₗ[R] Matrix m n R where
  toFun f := of fun i j => f (stdBasis R (fun _ => R) j 1) i
  invFun := Matrix.mulVecLin
  right_inv M := by
    ext i j
    simp only [Matrix.mulVec_stdBasis, Matrix.mulVecLin_apply, of_apply]
  left_inv f := by
    apply (Pi.basisFun R n).ext
    

Proof state:
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
⊢ ∀ (i : n),
    (mulVecLin
          (AddHom.toFun
            {
                toAddHom :=
                  { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                    map_add' :=
                      (_ :
                        ∀ (f g : (n → R) →ₗ[R] m → R),
                          (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                            (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                              (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) },
                map_smul' :=
                  (_ :
                    ∀ (c : R) (f : (n → R) →ₗ[R] m → R),
                      AddHom.toFun
                          { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                            map_add' :=
                              (_ :
                                ∀ (f g : (n → R) →ₗ[R] m → R),
                                  (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                    (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                      (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                          (c • f) =
                        (RingHom.id R) c •
                          AddHom.toFun
                            { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                              map_add' :=
                                (_ :
                                  ∀ (f g : (n → R) →ₗ[R] m → R),
                                    (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                      (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                        (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                            f) }.toAddHom
            f))
        ((Pi.basisFun R n) i) =
      f ((Pi.basisFun R n) i)

Next tactic:
intro j
/-- Linear maps `(n → R) →ₗ[R] (m → R)` are linearly equivalent to `Matrix m n R`. -/
def LinearMap.toMatrix' : ((n → R) →ₗ[R] m → R) ≃ₗ[R] Matrix m n R where
  toFun f := of fun i j => f (stdBasis R (fun _ => R) j 1) i
  invFun := Matrix.mulVecLin
  right_inv M := by
    ext i j
    simp only [Matrix.mulVec_stdBasis, Matrix.mulVecLin_apply, of_apply]
  left_inv f := by
    apply (Pi.basisFun R n).ext
    intro j; 

Proof state:
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
j : n
⊢ (mulVecLin
        (AddHom.toFun
          {
              toAddHom :=
                { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                  map_add' :=
                    (_ :
                      ∀ (f g : (n → R) →ₗ[R] m → R),
                        (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                          (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                            (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) },
              map_smul' :=
                (_ :
                  ∀ (c : R) (f : (n → R) →ₗ[R] m → R),
                    AddHom.toFun
                        { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                          map_add' :=
                            (_ :
                              ∀ (f g : (n → R) →ₗ[R] m → R),
                                (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                  (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                    (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                        (c • f) =
                      (RingHom.id R) c •
                        AddHom.toFun
                          { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                            map_add' :=
                              (_ :
                                ∀ (f g : (n → R) →ₗ[R] m → R),
                                  (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                    (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                      (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                          f) }.toAddHom
          f))
      ((Pi.basisFun R n) j) =
    f ((Pi.basisFun R n) j)

Next tactic:
ext i
/-- Linear maps `(n → R) →ₗ[R] (m → R)` are linearly equivalent to `Matrix m n R`. -/
def LinearMap.toMatrix' : ((n → R) →ₗ[R] m → R) ≃ₗ[R] Matrix m n R where
  toFun f := of fun i j => f (stdBasis R (fun _ => R) j 1) i
  invFun := Matrix.mulVecLin
  right_inv M := by
    ext i j
    simp only [Matrix.mulVec_stdBasis, Matrix.mulVecLin_apply, of_apply]
  left_inv f := by
    apply (Pi.basisFun R n).ext
    intro j; ext i
    

Proof state:
case h
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
j : n
i : m
⊢ (mulVecLin
        (AddHom.toFun
          {
              toAddHom :=
                { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                  map_add' :=
                    (_ :
                      ∀ (f g : (n → R) →ₗ[R] m → R),
                        (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                          (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                            (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) },
              map_smul' :=
                (_ :
                  ∀ (c : R) (f : (n → R) →ₗ[R] m → R),
                    AddHom.toFun
                        { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                          map_add' :=
                            (_ :
                              ∀ (f g : (n → R) →ₗ[R] m → R),
                                (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                  (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                    (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                        (c • f) =
                      (RingHom.id R) c •
                        AddHom.toFun
                          { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                            map_add' :=
                              (_ :
                                ∀ (f g : (n → R) →ₗ[R] m → R),
                                  (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                    (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                      (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                          f) }.toAddHom
          f))
      ((Pi.basisFun R n) j) i =
    f ((Pi.basisFun R n) j) i

Next tactic:
simp only [Pi.basisFun_apply, Matrix.mulVec_stdBasis, Matrix.mulVecLin_apply, of_apply]
/-- Linear maps `(n → R) →ₗ[R] (m → R)` are linearly equivalent to `Matrix m n R`. -/
def LinearMap.toMatrix' : ((n → R) →ₗ[R] m → R) ≃ₗ[R] Matrix m n R where
  toFun f := of fun i j => f (stdBasis R (fun _ => R) j 1) i
  invFun := Matrix.mulVecLin
  right_inv M := by
    

Proof state:
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
M : Matrix m n R
⊢ AddHom.toFun
      {
          toAddHom :=
            { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
              map_add' :=
                (_ :
                  ∀ (f g : (n → R) →ₗ[R] m → R),
                    (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                      (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                        (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) },
          map_smul' :=
            (_ :
              ∀ (c : R) (f : (n → R) →ₗ[R] m → R),
                AddHom.toFun
                    { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                      map_add' :=
                        (_ :
                          ∀ (f g : (n → R) →ₗ[R] m → R),
                            (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                              (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                    (c • f) =
                  (RingHom.id R) c •
                    AddHom.toFun
                      { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                        map_add' :=
                          (_ :
                            ∀ (f g : (n → R) →ₗ[R] m → R),
                              (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                  (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                      f) }.toAddHom
      (mulVecLin M) =
    M

Next tactic:
ext i j
/-- Linear maps `(n → R) →ₗ[R] (m → R)` are linearly equivalent to `Matrix m n R`. -/
def LinearMap.toMatrix' : ((n → R) →ₗ[R] m → R) ≃ₗ[R] Matrix m n R where
  toFun f := of fun i j => f (stdBasis R (fun _ => R) j 1) i
  invFun := Matrix.mulVecLin
  right_inv M := by
    ext i j
    

Proof state:
case a.h
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
M : Matrix m n R
i : m
j : n
⊢ AddHom.toFun
      {
          toAddHom :=
            { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
              map_add' :=
                (_ :
                  ∀ (f g : (n → R) →ₗ[R] m → R),
                    (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                      (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                        (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) },
          map_smul' :=
            (_ :
              ∀ (c : R) (f : (n → R) →ₗ[R] m → R),
                AddHom.toFun
                    { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                      map_add' :=
                        (_ :
                          ∀ (f g : (n → R) →ₗ[R] m → R),
                            (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                              (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                    (c • f) =
                  (RingHom.id R) c •
                    AddHom.toFun
                      { toFun := fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i,
                        map_add' :=
                          (_ :
                            ∀ (f g : (n → R) →ₗ[R] m → R),
                              (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) (f + g) =
                                (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) f +
                                  (fun f => of fun i j => f ((stdBasis R (fun x => R) j) 1) i) g) }
                      f) }.toAddHom
      (mulVecLin M) i j =
    M i j

Next tactic:
simp only [Matrix.mulVec_stdBasis, Matrix.mulVecLin_apply, of_apply]
@[simp]
theorem LinearMap.toMatrix'_apply (f : (n → R) →ₗ[R] m → R) (i j) :
    LinearMap.toMatrix' f i j = f (fun j' => if j' = j then 1 else 0) i := by
  

Proof state:
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
i : m
j : n
⊢ toMatrix' f i j = f (fun j' => if j' = j then 1 else 0) i

Next tactic:
simp only [LinearMap.toMatrix', LinearEquiv.coe_mk, of_apply]
@[simp]
theorem LinearMap.toMatrix'_apply (f : (n → R) →ₗ[R] m → R) (i j) :
    LinearMap.toMatrix' f i j = f (fun j' => if j' = j then 1 else 0) i := by
  simp only [LinearMap.toMatrix', LinearEquiv.coe_mk, of_apply]
  

Proof state:
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
i : m
j : n
⊢ f ((stdBasis R (fun x => R) j) 1) i = f (fun j' => if j' = j then 1 else 0) i

Next tactic:
refine congr_fun ?_ _
@[simp]
theorem LinearMap.toMatrix'_apply (f : (n → R) →ₗ[R] m → R) (i j) :
    LinearMap.toMatrix' f i j = f (fun j' => if j' = j then 1 else 0) i := by
  simp only [LinearMap.toMatrix', LinearEquiv.coe_mk, of_apply]
  refine congr_fun ?_ _  -- porting note: `congr` didn't do this
  

Proof state:
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
i : m
j : n
⊢ f ((stdBasis R (fun x => R) j) 1) = f fun j' => if j' = j then 1 else 0

Next tactic:
congr
@[simp]
theorem LinearMap.toMatrix'_apply (f : (n → R) →ₗ[R] m → R) (i j) :
    LinearMap.toMatrix' f i j = f (fun j' => if j' = j then 1 else 0) i := by
  simp only [LinearMap.toMatrix', LinearEquiv.coe_mk, of_apply]
  refine congr_fun ?_ _  -- porting note: `congr` didn't do this
  congr
  

Proof state:
case h.e_6.h
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
i : m
j : n
⊢ (stdBasis R (fun x => R) j) 1 = fun j' => if j' = j then 1 else 0

Next tactic:
ext j'
@[simp]
theorem LinearMap.toMatrix'_apply (f : (n → R) →ₗ[R] m → R) (i j) :
    LinearMap.toMatrix' f i j = f (fun j' => if j' = j then 1 else 0) i := by
  simp only [LinearMap.toMatrix', LinearEquiv.coe_mk, of_apply]
  refine congr_fun ?_ _  -- porting note: `congr` didn't do this
  congr
  ext j'
  

Proof state:
case h.e_6.h.h
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
i : m
j j' : n
⊢ (stdBasis R (fun x => R) j) 1 j' = if j' = j then 1 else 0

Next tactic:
split_ifs with h
@[simp]
theorem LinearMap.toMatrix'_apply (f : (n → R) →ₗ[R] m → R) (i j) :
    LinearMap.toMatrix' f i j = f (fun j' => if j' = j then 1 else 0) i := by
  simp only [LinearMap.toMatrix', LinearEquiv.coe_mk, of_apply]
  refine congr_fun ?_ _  -- porting note: `congr` didn't do this
  congr
  ext j'
  split_ifs with h
  · 

Proof state:
case pos
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
i : m
j j' : n
h : j' = j
⊢ (stdBasis R (fun x => R) j) 1 j' = 1

Next tactic:
rw [h, stdBasis_same]
@[simp]
theorem LinearMap.toMatrix'_apply (f : (n → R) →ₗ[R] m → R) (i j) :
    LinearMap.toMatrix' f i j = f (fun j' => if j' = j then 1 else 0) i := by
  simp only [LinearMap.toMatrix', LinearEquiv.coe_mk, of_apply]
  refine congr_fun ?_ _  -- porting note: `congr` didn't do this
  congr
  ext j'
  split_ifs with h
  · rw [h, stdBasis_same]
  

Proof state:
case neg
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
f : (n → R) →ₗ[R] m → R
i : m
j j' : n
h : ¬j' = j
⊢ (stdBasis R (fun x => R) j) 1 j' = 0

Next tactic:
apply stdBasis_ne _ _ _ _ h
@[simp]
theorem LinearMap.toMatrix'_id : LinearMap.toMatrix' (LinearMap.id : (n → R) →ₗ[R] n → R) = 1 := by
  

Proof state:
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
⊢ toMatrix' id = 1

Next tactic:
ext
@[simp]
theorem LinearMap.toMatrix'_id : LinearMap.toMatrix' (LinearMap.id : (n → R) →ₗ[R] n → R) = 1 := by
  ext
  

Proof state:
case a.h
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
i✝ x✝ : n
⊢ toMatrix' id i✝ x✝ = OfNat.ofNat 1 i✝ x✝

Next tactic:
rw [Matrix.one_apply, LinearMap.toMatrix'_apply, id_apply]
/-- Shortcut lemma for `Matrix.toLin'_mul` and `LinearMap.comp_apply` -/
theorem Matrix.toLin'_mul_apply [Fintype m] [DecidableEq m] (M : Matrix l m R) (N : Matrix m n R)
    (x) : Matrix.toLin' (M * N) x = Matrix.toLin' M (Matrix.toLin' N x) := by
  

Proof state:
R : Type u_1
inst✝⁴ : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝³ : DecidableEq n
inst✝² : Fintype n
inst✝¹ : Fintype m
inst✝ : DecidableEq m
M : Matrix l m R
N : Matrix m n R
x : n → R
⊢ (toLin' (M * N)) x = (toLin' M) ((toLin' N) x)

Next tactic:
rw [Matrix.toLin'_mul, LinearMap.comp_apply]
theorem LinearMap.toMatrix'_comp [Fintype l] [DecidableEq l] (f : (n → R) →ₗ[R] m → R)
    (g : (l → R) →ₗ[R] n → R) :
    LinearMap.toMatrix' (f.comp g) = LinearMap.toMatrix' f * LinearMap.toMatrix' g := by
  

Proof state:
R : Type u_1
inst✝⁴ : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝³ : DecidableEq n
inst✝² : Fintype n
inst✝¹ : Fintype l
inst✝ : DecidableEq l
f : (n → R) →ₗ[R] m → R
g : (l → R) →ₗ[R] n → R
⊢ toMatrix' (f ∘ₗ g) = toMatrix' f * toMatrix' g

Next tactic:
suffices f.comp g = Matrix.toLin' (LinearMap.toMatrix' f * LinearMap.toMatrix' g) by
    rw [this, LinearMap.toMatrix'_toLin']
theorem LinearMap.toMatrix'_comp [Fintype l] [DecidableEq l] (f : (n → R) →ₗ[R] m → R)
    (g : (l → R) →ₗ[R] n → R) :
    LinearMap.toMatrix' (f.comp g) = LinearMap.toMatrix' f * LinearMap.toMatrix' g := by
  suffices f.comp g = Matrix.toLin' (LinearMap.toMatrix' f * LinearMap.toMatrix' g) by
    

Proof state:
R : Type u_1
inst✝⁴ : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝³ : DecidableEq n
inst✝² : Fintype n
inst✝¹ : Fintype l
inst✝ : DecidableEq l
f : (n → R) →ₗ[R] m → R
g : (l → R) →ₗ[R] n → R
this : f ∘ₗ g = toLin' (toMatrix' f * toMatrix' g)
⊢ toMatrix' (f ∘ₗ g) = toMatrix' f * toMatrix' g

Next tactic:
rw [this, LinearMap.toMatrix'_toLin']
theorem LinearMap.toMatrix'_comp [Fintype l] [DecidableEq l] (f : (n → R) →ₗ[R] m → R)
    (g : (l → R) →ₗ[R] n → R) :
    LinearMap.toMatrix' (f.comp g) = LinearMap.toMatrix' f * LinearMap.toMatrix' g := by
  suffices f.comp g = Matrix.toLin' (LinearMap.toMatrix' f * LinearMap.toMatrix' g) by
    rw [this, LinearMap.toMatrix'_toLin']
  

Proof state:
R : Type u_1
inst✝⁴ : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝³ : DecidableEq n
inst✝² : Fintype n
inst✝¹ : Fintype l
inst✝ : DecidableEq l
f : (n → R) →ₗ[R] m → R
g : (l → R) →ₗ[R] n → R
⊢ f ∘ₗ g = toLin' (toMatrix' f * toMatrix' g)

Next tactic:
rw [Matrix.toLin'_mul, Matrix.toLin'_toMatrix', Matrix.toLin'_toMatrix']
@[simp]
theorem LinearMap.toMatrix'_algebraMap (x : R) :
    LinearMap.toMatrix' (algebraMap R (Module.End R (n → R)) x) = scalar n x := by
  

Proof state:
R : Type u_1
inst✝² : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝¹ : DecidableEq n
inst✝ : Fintype n
x : R
⊢ toMatrix' ((algebraMap R (Module.End R (n → R))) x) = (scalar n) x

Next tactic:
simp [Module.algebraMap_end_eq_smul_id, smul_eq_diagonal_mul]
/-- If `M` and `M'` are each other's inverse matrices, they provide an equivalence between `m → A`
and `n → A` corresponding to `M.mulVec` and `M'.mulVec`. -/
@[simps]
def Matrix.toLin'OfInv [Fintype m] [DecidableEq m] {M : Matrix m n R} {M' : Matrix n m R}
    (hMM' : M * M' = 1) (hM'M : M' * M = 1) : (m → R) ≃ₗ[R] n → R :=
  { Matrix.toLin' M' with
    toFun := Matrix.toLin' M'
    invFun := Matrix.toLin' M
    left_inv := fun x => by 

Proof state:
R : Type u_1
inst✝⁴ : CommSemiring R
k : Type u_2
l : Type u_3
m : Type u_4
n : Type u_5
inst✝³ : DecidableEq n
inst✝² : Fintype n
inst✝¹ : Fintype m
inst✝ : DecidableEq m
M : Matrix m n R
M' : Matrix n m R
hMM' : M * M' = 1
hM'M : M' * M = 1
src✝ : (m → R) →ₗ[R] n → R := toLin' M'
x : m → R
⊢ (toLin' M)
      (AddHom.toFun
        {
            toAddHom :=
              { toFun := ⇑(toLin' M'),
                map_add' :=
                  (_ :
                    ∀ (x y : m → R),
                      AddHom.toFun src✝.toAddHom (x + y) =
                        AddHom.toFun src✝.toAddHom x + AddHom.toFun src✝.toAddHom y) },
            map_smul' :=
              (_ :
                ∀ (r : R) (x : m → R),
                  AddHom.toFun src✝.toAddHom (r • x) = (RingHom.id R) r • AddHom.toFun src✝.toAddHom x) }.toAddHom
        x) =
    x

Next tactic:
rw [← Matrix.toLin'_mul_apply, hMM', Matrix.toLin'_one, id_apply]