Matrix Phylogeny
Seven pages have introduced classes of matrices — invertible, defective, normal, symmetric, positive definite, orthogonal, diagonal — and a decomposition for most of them. This page is the map.
The word phylogenetic describes how we capture the relationships among individuals or groups, and comes from the Greek words for “tribe” and “source”. A phylogenetic tree of matrices is exactly what Figure 4.13 draws: black arrows for is a subset of, blue labels for what you can do with it.
What you’ll learn
Section titled “What you’ll learn”- The whole tree: which matrix classes contain which, in the order the book presents them.
- Which decomposition attaches to each class, and what condition unlocks it.
- Why non-singular and non-defective are independent — the book’s own caveat, with a witness in each of the four quadrants.
- What normal means () and why it sits between non-defective and symmetric.
- A measured census: how often each construction of random matrix actually lands in each class.
- Which class
np.linalg.qrputs you in, which is not the one most people assume.
Intuition: two independent questions, then a chain of restrictions
Section titled “Intuition: two independent questions, then a chain of restrictions”The tree looks complicated because it answers two different questions at the same level.
The first is can you invert it? — decided by the determinant. The second is can you diagonalise it? — decided by whether there are independent eigenvectors. These are independent: a matrix can be either, both or neither. The book says so explicitly, and it is the most commonly mis-remembered fact in the chapter.
Below the non-defective branch, though, everything is a chain of tightening restrictions, and each tightening buys something:
with orthogonal hanging off normal in a different direction.
flowchart TD R["Real matrices A ∈ ℝⁿˣᵐ
∃ pseudo-inverse, ∃ SVD"] R --> NS["Non-square, n ≠ m
ℝⁿˣᵐ"] R --> SQ["Square, ℝⁿˣⁿ
∃ determinant, ∃ trace"] SQ -->|"det ≠ 0"| REG["Regular / invertible
∃ inverse matrix"] SQ -->|"det = 0"| SING1["Singular"] SQ -->|"basis of eigenvectors"| ND["Non-defective
(diagonalizable)
∃ eigendecomposition"] SQ -->|"no basis of eigenvectors"| DEF["Defective"] ND -->|"AᵀA = AAᵀ"| NORM["Normal"] ND -->|"AᵀA ≠ AAᵀ"| NONNORM["Non-normal"] NORM -->|"AᵀA = AAᵀ = I"| ORTH["Orthogonal
Aᵀ = A⁻¹
columns are orthonormal"] ORTH --> ROT["Rotation
det = +1"] ORTH -->|"det ≠ 0"| REG NORM --> SYM["Symmetric, S = Sᵀ
eigenvalues ∈ ℝ"] SYM --> PD["Positive definite
xᵀPx > 0
∃ Cholesky
eigenvalues > 0"] PD -->|"det ≠ 0"| REG SYM --> DIAG["Diagonal D"] DIAG --> ID["Identity matrix I"]
That is the book’s Figure 4.13, with the blue operations folded into the boxes.
The math
Section titled “The math”The trunk: every real matrix
Section titled “The trunk: every real matrix”For all real matrices , the pseudo-inverse and the SVD exist. That is the widest statement in the chapter, and it is why §4.5 came last: it needs no hypothesis at all.
For non-square matrices () that is where the tree stops. There is no determinant, no trace, no eigenvalue — those all require a square matrix, since needs to live in the same space as .
The first fork: invertibility
Section titled “The first fork: invertibility”Focusing on square matrices , the determinant informs us whether the matrix possesses an inverse — that is, whether it belongs to the class of regular, invertible matrices. This is §4.1’s Theorem 4.1: if and only if exists.
The second fork: diagonalisability
Section titled “The second fork: diagonalisability”If the square matrix possesses linearly independent eigenvectors, then the matrix is non-defective and an eigendecomposition exists (§4.4’s Theorem 4.20; the sufficient condition of distinct eigenvalues is Theorem 4.12). Repeated eigenvalues may result in defective matrices, which cannot be diagonalized.
Down the non-defective branch: normal
Section titled “Down the non-defective branch: normal”This is the condition that makes the two Gram matrices of §4.5 coincide — and therefore makes the left- and right-singular vectors the same, which is exactly why normal matrices are the ones whose SVD and eigendecomposition line up. Over the reals, normal is the natural home of “diagonalisable by an orthogonal change of basis”.
If the more restrictive condition holds that
then is orthogonal (Definition 3.8). The set of orthogonal matrices is a subset of the regular matrices and satisfies — the cheapest inverse in linear algebra. Orthogonal matrices with are rotations; with they are reflections.
Symmetric, and below
Section titled “Symmetric, and below”Normal matrices have a frequently encountered subset, the symmetric matrices satisfying . Symmetric matrices have only real eigenvalues — the spectral theorem, 4.15, which the chapter has leaned on repeatedly.
A subset of the symmetric matrices consists of the positive definite matrices satisfying
In this case a unique Cholesky decomposition exists (Theorem 4.18). Positive definite matrices have only positive eigenvalues and are always invertible — a nonzero determinant follows, since the determinant is the product of the eigenvalues.
Another subset of the symmetric matrices consists of the diagonal matrices . Diagonal matrices are closed under multiplication and addition, but do not necessarily form a group — that is only the case if all diagonal entries are nonzero, so that the matrix is invertible. A special diagonal matrix is the identity .
Worked example by hand
Section titled “Worked example by hand”Every class, on one matrix each
Section titled “Every class, on one matrix each”| matrix | invertible | non-defective | normal | symmetric | pos. def. | orthogonal | diagonal |
|---|---|---|---|---|---|---|---|
| no | no | no | no | no | no | no | |
| yes | no | no | no | no | no | no | |
| yes | yes | no | no | no | no | no | |
| yes | yes over , no over | yes | no | no | yes | no | |
| yes | yes | yes | yes | yes | no | no | |
| yes | yes | yes | yes | no | no | no | |
| yes | yes | yes | yes | yes | no | yes | |
| yes | yes | yes | yes | yes | yes | yes |
Two rows repay attention.
Row 4, the rotation , is normal and orthogonal, with
eigenvalues . So “normal” does not imply “real eigenvalues” — only symmetric does. Over
it has two distinct eigenvalues and two independent eigenvectors, so it is perfectly
diagonalisable there; over there is no eigenvector at all. This is why the book’s caveat
says “not diagonalizable in the real numbers”, and why the entry in that column needs a field, not
just a yes or no. A numerical classifier built on np.linalg.eigvals, which returns complex arrays, will
report it as non-defective — correctly, over .
Row 6, , is symmetric with eigenvalues — real, as the spectral theorem demands, but one is negative, so it is not positive definite and has no Cholesky. Symmetry gets you real eigenvalues; positive definiteness is a further condition.
Verified
Section titled “Verified”import numpy as np
TOL = 1e-8
def is_defective(M, tol=1e-7):
n = M.shape[0]
seen, total = [], 0
for lam in np.linalg.eigvals(M):
if any(abs(lam - u) < 1e-6 for u in seen):
continue
seen.append(lam)
s = np.linalg.svd(M - lam * np.eye(n), compute_uv=False)
total += int(np.sum(s < tol * max(1.0, float(s[0]))))
return total < n
def classify(M):
n = M.shape[0]
sym = bool(np.allclose(M, M.T, atol=TOL))
posdef = False
if sym:
try:
np.linalg.cholesky(M)
posdef = True
except np.linalg.LinAlgError:
posdef = False
return {
"invertible": abs(float(np.linalg.det(M))) > TOL,
"non-defect": not is_defective(M),
"normal": bool(np.allclose(M.T @ M, M @ M.T, atol=TOL)),
"symmetric": sym,
"pos.def": posdef,
"orthogonal": bool(np.allclose(M.T @ M, np.eye(n), atol=TOL)),
"diagonal": bool(np.allclose(M, np.diag(np.diag(M)), atol=TOL)),
}
cases = {
"nilpotent [[0,1],[0,0]]": [[0.0, 1], [0, 0]],
"Jordan [[2,1],[0,2]]": [[2.0, 1], [0, 2]],
"generic [[4,2],[1,3]]": [[4.0, 2], [1, 3]],
"rotation [[0,-1],[1,0]]": [[0.0, -1], [1, 0]],
"SPD [[2,1],[1,2]]": [[2.0, 1], [1, 2]],
"indefinite [[2,1],[1,-2]]": [[2.0, 1], [1, -2]],
"diagonal [[3,0],[0,2]]": [[3.0, 0], [0, 2]],
"identity [[1,0],[0,1]]": [[1.0, 0], [0, 1]],
}
keys = list(classify(np.eye(2)).keys())
print(f"{'matrix':26}" + "".join(f"{k:>12}" for k in keys) + f"{'eigenvalues':>26}")
for name, M in cases.items():
M = np.asarray(M, dtype=float)
c = classify(M)
ev = np.linalg.eigvals(M)
evs = ", ".join(f"{v.real:+.3f}{v.imag:+.3f}j" if abs(v.imag) > 1e-12 else f"{v.real:+.3f}"
for v in ev)
print(f"{name:26}" + "".join(f"{('yes' if c[k] else 'no'):>12}" for k in keys) + f"{evs:>26}")matrix invertible non-defect normal symmetric pos.def orthogonal diagonal eigenvalues
nilpotent [[0,1],[0,0]] no no no no no no no +0.000, +0.000
Jordan [[2,1],[0,2]] yes no no no no no no +2.000, +2.000
generic [[4,2],[1,3]] yes yes no no no no no +5.000, +2.000
rotation [[0,-1],[1,0]] yes yes yes no no yes no+0.000+1.000j, +0.000-1.000j
SPD [[2,1],[1,2]] yes yes yes yes yes no no +3.000, +1.000
indefinite [[2,1],[1,-2]] yes yes yes yes no no no +2.236, -2.236
diagonal [[3,0],[0,2]] yes yes yes yes yes no yes +3.000, +2.000
identity [[1,0],[0,1]] yes yes yes yes yes yes yes +1.000, +1.000Read down the columns and the tree appears. Every yes in pos.def has a yes in symmetric to
its left, which has a yes in normal, which has a yes in non-defect. The containments hold in
every row, which is what a tree of subsets should look like.
Two rows show where the tree branches rather than nests. The Jordan row is invertible yes with
non-defect no — the book’s caveat, and note that nothing to its right is yes either, because a
defective matrix cannot be normal. The rotation row is normal yes with symmetric no, and its
eigenvalue column is the only complex one: . That is the pair to remember — normal buys you an
orthogonal diagonalisation, but only symmetry buys you real eigenvalues.
Notice also that this classifier reports the rotation as non-defect yes, because np.linalg.eigvals
works over and finds two distinct eigenvalues with two independent eigenvectors there. That
is the right answer to the question the code asks. It is not the answer to the question the book asks,
which is about — and the discrepancy is a reminder that “diagonalisable” is incomplete
without a field.
See it move
Section titled “See it move”Determinant +1, so certainly invertible. But its characteristic polynomial is lambda squared plus one, whose roots are plus and minus i — so there is no real eigenvector and no real eigendecomposition. This is the book's own counterexample to the idea that non-singular and non-defective are the same.
From scratch
Section titled “From scratch”import numpy as np
TOL = 1e-8
PROPS = ["invertible", "non-defective", "normal", "symmetric",
"pos. definite", "orthogonal", "diagonal", "rotation"]
def is_defective(M, tol=1e-7):
n = M.shape[0]
seen, total = [], 0
for lam in np.linalg.eigvals(M):
if any(abs(lam - u) < 1e-6 for u in seen):
continue
seen.append(lam)
s = np.linalg.svd(M - lam * np.eye(n), compute_uv=False)
total += int(np.sum(s < tol * max(1.0, float(s[0]))))
return total < n
def classify(M):
n = M.shape[0]
sym = bool(np.allclose(M, M.T, atol=TOL))
posdef = False
if sym:
try:
np.linalg.cholesky(M)
posdef = True
except np.linalg.LinAlgError:
posdef = False
orth = bool(np.allclose(M.T @ M, np.eye(n), atol=TOL))
return {
"invertible": abs(float(np.linalg.det(M))) > TOL,
"non-defective": not is_defective(M),
"normal": bool(np.allclose(M.T @ M, M @ M.T, atol=TOL)),
"symmetric": sym,
"pos. definite": posdef,
"orthogonal": orth,
"diagonal": bool(np.allclose(M, np.diag(np.diag(M)), atol=TOL)),
"rotation": orth and float(np.linalg.det(M)) > 0,
}
rng = np.random.default_rng(41)
n = 3
def jordan():
J = np.eye(n); J[0, 1] = 1.0
S = rng.normal(size=(n, n))
while abs(np.linalg.det(S)) < 0.3:
S = rng.normal(size=(n, n))
return S @ J @ np.linalg.inv(S)
families = [
("Gaussian", lambda: rng.normal(size=(n, n))),
("small integer", lambda: rng.integers(-2, 3, size=(n, n)).astype(float)),
("symmetric", lambda: (lambda M: M + M.T)(rng.normal(size=(n, n)))),
("SPD", lambda: (lambda M: M @ M.T + n * np.eye(n))(rng.normal(size=(n, n)))),
("orthogonal", lambda: np.linalg.qr(rng.normal(size=(n, n)))[0]),
("diagonal", lambda: np.diag(rng.normal(size=n))),
("Jordan-like", jordan),
]
trials = 1200
print(f"{'construction':>15}" + "".join(f"{p[:13]:>15}" for p in PROPS))
for name, make in families:
hits = np.zeros(len(PROPS))
for _ in range(trials):
c = classify(make())
hits += np.array([1.0 if c[p] else 0.0 for p in PROPS])
pct = 100.0 * hits / trials
print(f"{name:>15}" + "".join(f"{v:>15.2f}" for v in pct)) construction invertible non-defective normal symmetric pos. definite orthogonal diagonal rotation
Gaussian 100.00 100.00 0.00 0.00 0.00 0.00 0.00 0.00
small integer 83.83 94.33 0.67 0.58 0.00 0.00 0.00 0.00
symmetric 100.00 100.00 100.00 100.00 2.50 0.00 0.00 0.00
SPD 100.00 100.00 100.00 100.00 100.00 0.00 0.00 0.00
orthogonal 100.00 100.00 100.00 0.00 0.00 100.00 0.00 100.00
diagonal 100.00 100.00 100.00 100.00 12.67 0.00 100.00 0.00
Jordan-like 100.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00Six readings, in order of how surprising they are.
The Jordan-like row is the book’s counterexample, sampled. invertible, non-defective. The two properties do not merely fail to imply each other in principle; you can generate a thousand matrices that split them.
The diagonal row’s positive definite is a coin-flip check. A diagonal matrix with three independent standard-normal entries is positive definite exactly when all three are positive, which has probability . Measuring over draws confirms the classifier is testing what it claims to.
The symmetric row is only positive definite. Symmetry gets you real eigenvalues, not positive ones. for Gaussian has eigenvalues spread either side of zero, and needing all three positive is rare. The book’s chain symmetric positive definite is a strict containment, and this is how strict.
The Gaussian row has zeros in five of eight columns, and they will never fill in. Symmetry requires exactly, an equality between two independent continuous random variables — probability zero. All the structured classes are measure-zero coincidences, which is why every one of them has to be constructed.
Small-integer matrices are only invertible. Over a range of five integers, happens. And non-defective — repeats become possible once entries are discrete, exactly as §4.4’s census found.
The orthogonal row is rotation, and that is an artefact of . np.linalg.qr returns a
with , which is for . In any even dimension the
same code returns reflections, every time. The last figure on this page measures it.
On real data
Section titled “On real data”Reading the plot
Section titled “Reading the plot”From the census heatmap. Read the zeros, not the hundreds. Five of the eight columns are empty in the Gaussian row, and no amount of sampling changes that — symmetry, normality, orthogonality and diagonality are all exact equalities between continuous quantities, so their probability is zero. Every interesting class in this chapter has to be built, and that is why the book’s tree is a tree of constructions rather than a partition of the typical case.
The two rows that are not zero-or-one are the informative ones: small integer at invertible
and non-defective, and diagonal at positive definite. The last one is a check on the
classifier, since the theoretical value is .
From the implications heatmap. The cells are the tree’s black arrows, recovered from data: symmetric normal, positive definite symmetric normal non-defective, orthogonal normal, diagonal symmetric. None of those needed to be told to the sampler; they fall out.
The cells that are not are where the tree branches rather than nests:
| given | also has | share |
|---|---|---|
| invertible | non-defective | |
| non-defective | invertible | |
| normal | symmetric | |
| symmetric | positive definite | |
| symmetric | orthogonal | |
| orthogonal | symmetric |
The first two rows are the book’s caveat as a pair of numbers: neither direction is an implication. The last two are worth noticing too — in this sample no orthogonal matrix was symmetric and vice versa. That is not a theorem (the identity and any reflection matrix are both) but it reflects that the two branches leave normal in different directions, so a matrix in both is a further coincidence.
From the four-quadrant figure. Read the defective and invertible lines in each box. All four
pairs appear, which is the definition of independent. The book names the
rotation matrix as its example and puts it in the top-right quadrant; the figure uses
there instead, because a repeated real eigenvalue makes the
failure visible without leaving the reals. Both work; the rotation’s failure is complex eigenvalues, the
Jordan block’s is a deficient eigenspace.
From the QR figure. This is the practical one, and it corrects a widespread assumption. Ask for a
random orthogonal matrix with np.linalg.qr(np.random.normal(size=(n,n)))[0] and you do not get a
uniformly random element of the orthogonal group — you get one whose determinant is
, deterministically. Over trials across eleven sizes there was not one exception.
The reason is the algorithm: Householder QR builds from reflections, and each reflection has determinant , so . For that is , which is why the census row said rotation — a fact about three dimensions, not about QR. In the same call returns a reflection every time. If you need a rotation, negate a column when the determinant is negative.
Pitfalls
Section titled “Pitfalls”Compare
Section titled “Compare”| class | defining condition | what it unlocks | cost of the inverse |
|---|---|---|---|
| real, any shape | none | SVD, pseudo-inverse | pseudo-inverse, |
| square | determinant, trace, eigenvalues | — | |
| invertible | LU, | ||
| non-defective | independent eigenvectors | , matrix powers | via the eigendecomposition |
| normal | singular and eigen-directions align | — | |
| symmetric | spectral theorem: real , orthonormal eigenbasis, | via eigh | |
| positive definite | unique Cholesky, , sampling | Cholesky, | |
| orthogonal | , lengths and angles preserved | free — transpose | |
| diagonal | for | everything elementwise | reciprocals |
| identity | — | itself |
The right-hand column is the whole chapter in one view: the further down the tree, the cheaper everything gets. That is what a decomposition buys — it moves your matrix down the tree.
-
The book explicitly warns that non-singular and non-defective are not the same. What is its example?
Measured, the two properties split both ways: 85.0 percent of sampled invertible matrices were non-defective, and 98.0 percent of non-defective ones were invertible. Neither is an implication.
pch.quizShowAnswer
B — A rotation matrix: its determinant is nonzero so it is invertible, but its eigenvalues are not real so it is not diagonalizable over the reals — Measured, the two properties split both ways: 85.0 percent of sampled invertible matrices were non-defective, and 98.0 percent of non-defective ones were invertible. Neither is an implication.
-
Where does 'eigenvalues are real' sit in the tree, and why not one level higher?
Over the complex numbers every normal matrix is unitarily diagonalizable, which is why the distinction is easy to lose. The book's tree places the real-eigenvalue claim on symmetric deliberately.
pch.quizShowAnswer
B — On the symmetric box. A rotation matrix is normal and has eigenvalues plus and minus i, so normality alone does not give real eigenvalues — over the reals you need symmetry — Over the complex numbers every normal matrix is unitarily diagonalizable, which is why the distinction is easy to lose. The book's tree places the real-eigenvalue claim on symmetric deliberately.
-
A Gaussian random 3x3 matrix was symmetric in 0 of 1200 trials. Will more sampling change that?
The same holds for normal, orthogonal and diagonal. Every structured class in the tree is a measure-zero condition, which is why they all have to be constructed rather than found.
pch.quizShowAnswer
B — No. Symmetry requires a-ij to equal a-ji exactly — an equality between two independent continuous random variables, which has probability zero — The same holds for normal, orthogonal and diagonal. Every structured class in the tree is a measure-zero condition, which is why they all have to be constructed rather than found.
-
The census found random diagonal matrices positive definite 12.67 percent of the time. What does that number check?
A measurement that lands on a value you can derive independently is worth more than one that merely looks plausible. Compare the symmetric row's 2.50 percent, which has no such simple closed form.
pch.quizShowAnswer
B — The classifier itself: a diagonal matrix with three independent standard-normal entries is positive definite exactly when all three are positive, so the theoretical rate is one in eight, 12.5 percent — A measurement that lands on a value you can derive independently is worth more than one that merely looks plausible. Compare the symmetric row's 2.50 percent, which has no such simple closed form.
-
np.linalg.qr on a random Gaussian matrix returns a Q with determinant (-1) to the (n-1), with zero exceptions in 4400 trials. Why?
This is why the census row for the orthogonal family showed 100 percent rotation: n was 3, so (-1) to the 2 is plus one. It is a fact about three dimensions, not about QR. For a Haar-random orthogonal matrix you must correct the column signs using the diagonal of R.
pch.quizShowAnswer
B — Householder QR builds Q from n-1 reflections and each reflection has determinant minus one, so the product is determined by n alone — meaning in every even dimension you get a reflection, never a rotation — This is why the census row for the orthogonal family showed 100 percent rotation: n was 3, so (-1) to the 2 is plus one. It is a fact about three dimensions, not about QR. For a Haar-random orthogonal matrix you must correct the column signs using the diagonal of R.
🧪 Try It Yourself
Section titled “🧪 Try It Yourself”Exercise 1 – Classify eight matrices
Section titled “Exercise 1 – Classify eight matrices”Exercise 2 – All four quadrants
Section titled “Exercise 2 – All four quadrants”Exercise 3 – The census
Section titled “Exercise 3 – The census”Exercise 4 – What np.linalg.qr actually returns
Section titled “Exercise 4 – What np.linalg.qr actually returns”Exercise 5 – Which decomposition applies?
Section titled “Exercise 5 – Which decomposition applies?”Recall card
Section titled “Recall card”- The SVD and pseudo-inverse exist for every real matrix; determinant, trace and eigenvalues need a square one.
- The determinant decides invertibility; the eigenvector count decides diagonalisability, and these are two independent questions.
- Non-singular and non-defective are not the same — the book’s example is a rotation matrix, invertible with complex eigenvalues. Measured, the split runs 85.0 percent one way and 98.0 percent the other, and all four combinations have small witnesses.
- Normal means A-transpose A equals A A-transpose, which is what makes the singular and eigen directions align.
- Orthogonal is the stricter A-transpose A equals A A-transpose equals I, giving the free inverse A-transpose; determinant plus one is a rotation, minus one a reflection.
- Symmetric is a subset of normal and is where real eigenvalues live — normality alone does not give them.
- Positive definite is a subset of symmetric, with a unique Cholesky, positive eigenvalues and a nonzero determinant. Only 38.8 percent of sampled symmetric matrices qualified.
- Diagonal matrices are closed under multiplication and addition but form a group only when every entry is nonzero; the identity is a special diagonal matrix.
- Every structured class is measure-zero: a Gaussian matrix was symmetric, normal, orthogonal or diagonal in zero of 1200 trials, because each condition is an exact equality between continuous quantities.
- np.linalg.qr returns a Q with determinant (-1) to the (n-1), exactly — so in every even dimension it is a reflection, not a rotation, with zero exceptions in 4400 trials.
Next: Chapter 4 Exercises and Solutions — all twelve of the book’s exercises, worked and verified.
pch.coffeeTagline
pch.coffeeCtapch.feedbackHeading
pch.feedbackSubheading