Theorem: Matrix.mulVec_surjective_iff_exists_right_inverse
File: Mathlib/LinearAlgebra/Matrix/NonsingularInverse.lean

tactic: cases nonempty_fintype m
state_before: l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
⊢ Function.Surjective A.mulVec ↔ ∃ B, A * B = 1
state_after: case intro
l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
val✝ : Fintype m
⊢ Function.Surjective A.mulVec ↔ ∃ B, A * B = 1

tactic: refine ⟨fun h ↦ ?_, fun ⟨B, hBA⟩ y ↦ ⟨B *ᵥ y, by simp [hBA]⟩⟩
state_before: case intro
l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
val✝ : Fintype m
⊢ Function.Surjective A.mulVec ↔ ∃ B, A * B = 1
state_after: case intro
l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
val✝ : Fintype m
h : Function.Surjective A.mulVec
⊢ ∃ B, A * B = 1

tactic: refine ⟨(Matrix.of cols)ᵀ, Matrix.ext fun i j ↦ ?_⟩
state_before: case intro
l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
val✝ : Fintype m
h : Function.Surjective A.mulVec
cols : m → n → R
hcols : ∀ (x : m), A *ᵥ cols x = Pi.single x 1
⊢ ∃ B, A * B = 1
state_after: case intro
l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
val✝ : Fintype m
h : Function.Surjective A.mulVec
cols : m → n → R
hcols : ∀ (x : m), A *ᵥ cols x = Pi.single x 1
i j : m
⊢ (A * (of cols)ᵀ) i j = 1 i j

tactic: rw [one_eq_pi_single, Pi.single_comm, ← hcols j]
state_before: case intro
l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
val✝ : Fintype m
h : Function.Surjective A.mulVec
cols : m → n → R
hcols : ∀ (x : m), A *ᵥ cols x = Pi.single x 1
i j : m
⊢ (A * (of cols)ᵀ) i j = 1 i j
state_after: case intro
l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
val✝ : Fintype m
h : Function.Surjective A.mulVec
cols : m → n → R
hcols : ∀ (x : m), A *ᵥ cols x = Pi.single x 1
i j : m
⊢ (A * (of cols)ᵀ) i j = (A *ᵥ cols j) i

tactic: rfl
state_before: case intro
l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
val✝ : Fintype m
h : Function.Surjective A.mulVec
cols : m → n → R
hcols : ∀ (x : m), A *ᵥ cols x = Pi.single x 1
i j : m
⊢ (A * (of cols)ᵀ) i j = (A *ᵥ cols j) i
state_after: no goals

tactic: simp [hBA]
state_before: l : Type u_1
m : Type u
n : Type u'
α : Type v
inst✝⁴ : DecidableEq m
inst✝³ : DecidableEq n
R : Type u_2
inst✝² : Semiring R
inst✝¹ : Finite m
inst✝ : Fintype n
A : Matrix m n R
val✝ : Fintype m
x✝ : ∃ B, A * B = 1
y : m → R
B : Matrix n m R
hBA : A * B = 1
⊢ A *ᵥ B *ᵥ y = y
state_after: no goals