Skip to content

feat(LinearAlgebra/Matrix/MoorePenrose): define the Moore-Penrose pseudo-inverse#36889

Open
KryptosAI wants to merge 7 commits intoleanprover-community:masterfrom
KryptosAI:feat/moore-penrose-inverse
Open

feat(LinearAlgebra/Matrix/MoorePenrose): define the Moore-Penrose pseudo-inverse#36889
KryptosAI wants to merge 7 commits intoleanprover-community:masterfrom
KryptosAI:feat/moore-penrose-inverse

Conversation

@KryptosAI
Copy link
Copy Markdown
Contributor

@KryptosAI KryptosAI commented Mar 20, 2026

Defines IsMoorePenroseInverse and constructs the Moore-Penrose pseudo-inverse for matrices over RCLike fields. Closes #24787.

Defs.lean defines the predicate using the heterogeneous four-condition characterization from the issue, plus uniqueness for semigroups with StarMul.

Basic.lean constructs the inverse via orthogonal projection and ker(f)ᗮ ≃ₗ range(f), then proves:

theorem exists_isMoorePenroseInverse (A : Matrix m n 𝕜) :
    ∃ (As : Matrix n m 𝕜), IsMoorePenroseInverse A As

def moorePenroseInverse (A : Matrix m n 𝕜) : Matrix n m 𝕜

lemma moorePenroseInverse_conjTranspose :
    moorePenroseInverse (Aᴴ) = (moorePenroseInverse A)ᴴ

lemma moorePenroseInverse_eq_nonsing_inv (hA : IsUnit A) :
    moorePenroseInverse A = A⁻¹

AI disclosure

  • Gemini 2.5 Pro: proof planning, initial code, edits
  • Claude Code (Opus 4.6): debugging, compilation, type-checking against mathlib4

I reviewed and directed all changes.


Open in Gitpod

@github-actions github-actions bot added the new-contributor This PR was made by a contributor with at most 5 merged PRs. Welcome to the community! label Mar 20, 2026
@github-actions
Copy link
Copy Markdown

Welcome new contributor!

Thank you for contributing to Mathlib! If you haven't done so already, please review our contribution guidelines, as well as the style guide and naming conventions. In particular, we kindly remind contributors that we have guidelines regarding the use of AI when making pull requests.

We use a review queue to manage reviews. If your PR does not appear there, it is probably because it is not successfully building (i.e., it doesn't have a green checkmark), has the awaiting-author tag, or another reason described in the Lifecycle of a PR. The review dashboard has a dedicated webpage which shows whether your PR is on the review queue, and (if not), why.

If you haven't already done so, please come to https://leanprover.zulipchat.com/, introduce yourself, and mention your new PR.

Thank you again for joining our community.

@github-actions
Copy link
Copy Markdown

github-actions bot commented Mar 20, 2026

PR summary 6ef8cc2731

Import changes for modified files

No significant changes to the import graph

Import changes for all files
Files Import difference
Mathlib.LinearAlgebra.Matrix.MoorePenrose.Defs (new file) 496
Mathlib.LinearAlgebra.Matrix.MoorePenrose.Basic (new file) 2145

Declarations diff

+ IsMoorePenroseInverse
+ _root_.IsMoorePenroseInverse.eq_moorePenroseInverse
+ exists_isMoorePenroseInverse
+ isMoorePenroseInverse_moorePenroseInverse
+ isMoorePenroseInverse_unique
+ isSelfAdjoint_mul
+ isSelfAdjoint_mul'
+ moorePenroseInverse
+ moorePenroseInverse_conjTranspose
+ moorePenroseInverse_eq_nonsing_inv
+ moorePenroseInverse_moorePenroseInverse
+ moorePenroseInverse_mul_self_mul
+ moorePenroseInverse_one
+ moorePenroseInverse_zero
+ mul_moorePenroseInverse_mul
+ star_moorePenroseInverse_mul
+ star_mul_moorePenroseInverse
+ symm
+ unique

You can run this locally as follows
## summary with just the declaration names:
./scripts/pr_summary/declarations_diff.sh <optional_commit>

## more verbose report:
./scripts/pr_summary/declarations_diff.sh long <optional_commit>

The doc-module for scripts/pr_summary/declarations_diff.sh contains some details about this script.


No changes to technical debt.

You can run this locally as

./scripts/reporting/technical-debt-metrics.sh pr_summary
  • The relative value is the weighted sum of the differences with weight given by the inverse of the current value of the statistic.
  • The absolute value is the relative value divided by the total sum of the inverses of the current values (i.e. the weighted average of the differences).

@github-actions github-actions bot added the t-algebra Algebra (groups, rings, fields, etc) label Mar 20, 2026
@KryptosAI KryptosAI force-pushed the feat/moore-penrose-inverse branch from d3c3c79 to bb46eca Compare March 20, 2026 05:54
@KryptosAI KryptosAI force-pushed the feat/moore-penrose-inverse branch from bb46eca to 1f2d10b Compare March 20, 2026 05:57
@robin-carlier robin-carlier added the LLM-generated PRs with substantial input from LLMs - review accordingly label Mar 20, 2026
Copy link
Copy Markdown
Collaborator

@vihdzp vihdzp left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unfamiliar with the mathematics, my comments are mostly stylistic.


## References

* <https://github.com/leanprover-community/mathlib4/issues/24787>
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We probably don't want to cite ourselves.

Suggested change
* <https://github.com/leanprover-community/mathlib4/issues/24787>

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done, removed.

2. `As * A * As = As`
3. `A * As` is self-adjoint (`star (A * As) = A * As`)
4. `As * A` is self-adjoint (`star (As * A) = As * A`) -/
def IsMoorePenroseInverse {α β γ δ} [HMul α β γ] [HMul β α δ] [HMul γ α α]
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we make this into a structure, so we can give names to the four conditions?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done — converted to a structure with named fields. Also added attribute [simp] on all four projections and updated symm to use where syntax.


## References

* <https://github.com/leanprover-community/mathlib4/issues/24787>
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
* <https://github.com/leanprover-community/mathlib4/issues/24787>

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done.

import Mathlib.LinearAlgebra.Matrix.MoorePenrose.Defs

/-!
# The Moore-Penrose Pseudo-Inverse for Matrices
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
# The Moore-Penrose Pseudo-Inverse for Matrices
# The Moore-Penrose pseudo-inverse for matrices

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done.

Kᗮ.subtype ∘ₗ e.symm.toLinearMap ∘ₗ
(Submodule.orthogonalProjection W : _ →L[𝕜] _).toLinearMap
let As : Matrix n m 𝕜 :=
(Matrix.toEuclideanLin (𝕜 := 𝕜) (m := n) (n := m)).symm g
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why not use this as the definition, instead of extracting this out with choice?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good call — moorePenroseInverse now uses the explicit construction directly. exists_isMoorePenroseInverse is a trivial corollary.

The construction uses the restricted isomorphism `ker(f)ᗮ ≃ₗ range(f)`
and orthogonal projections. -/
theorem exists_isMoorePenroseInverse (A : Matrix m n 𝕜) :
∃ (As : Matrix n m 𝕜), IsMoorePenroseInverse A As := by
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
(As : Matrix n m 𝕜), IsMoorePenroseInverse A As := by
∃ As : Matrix n m 𝕜, IsMoorePenroseInverse A As := by

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done.

(exists_isMoorePenroseInverse A).choose_spec

@[simp]
lemma moorePenroseInverse_zero : moorePenroseInverse (0 : Matrix m n 𝕜) = 0 := by
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might be worth having a IsMoorePenroseInverse.eq lemma stating IsMoorePenroseInverse A B → moorePenroseInverse A = B .

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added as IsMoorePenroseInverse.eq_moorePenroseInverse. Used it to simplify moorePenroseInverse_zero, moorePenroseInverse_one, moorePenroseInverse_moorePenroseInverse, moorePenroseInverse_conjTranspose, and moorePenroseInverse_eq_nonsing_inv.

apply isMoorePenroseInverse_unique (isMoorePenroseInverse_moorePenroseInverse 1)
exact ⟨by simp, by simp, by simp, by simp⟩

/-- The four Penrose conditions hold for `A` and `moorePenroseInverse A`. -/
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems weird to only comment this on the first one. I think the easiest way to fix this is to just remove the remark.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done, removed.

KryptosAI and others added 2 commits March 20, 2026 08:24
- Convert `IsMoorePenroseInverse` from a conjunction to a structure
  with named fields for the four Penrose conditions.
- Define `moorePenroseInverse` via the explicit construction instead
  of `Classical.choose`.
- Add `IsMoorePenroseInverse.eq_moorePenroseInverse` convenience lemma.
- Remove self-citation from references, fix module doc, style fixes.

Co-Authored-By: Claude Opus 4.6 <[email protected]>
@KryptosAI
Copy link
Copy Markdown
Contributor Author

thank you so much for the review! i think all have been addressed now.

@dagurtomas dagurtomas removed their assignment Apr 1, 2026
@dagurtomas dagurtomas requested a review from eric-wieser April 1, 2026 16:01
Comment on lines +43 to +45
/-- Heterogeneous uniqueness for matrices. -/
lemma isMoorePenroseInverse_unique {A : Matrix m n 𝕜} {B C : Matrix n m 𝕜}
(hB : IsMoorePenroseInverse A B) (hC : IsMoorePenroseInverse A C) : B = C := by
Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Isn't this a duplicate of a lemma you wrote in the other file?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not quite: IsMoorePenroseInverse.unique in Defs is the homogeneous semigroup lemma, so for matrices it only covers the square case where A, B, and C all have the same type. This lemma is the rectangular Matrix m n / Matrix n m specialization. I added a short note in e1939ce to make that distinction explicit.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This probably belongs in Analysis/Matrix since it import analysis stuff.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

LLM-generated PRs with substantial input from LLMs - review accordingly new-contributor This PR was made by a contributor with at most 5 merged PRs. Welcome to the community! t-algebra Algebra (groups, rings, fields, etc)

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Add the Moore-Penrose pseudo-inverse

7 participants