OrthogonalMatrixQ
Details and Options
- A p×q matrix m is orthogonal if p≥q and Transpose[m].m is the q×q identity matrix, or p≤q and m.Transpose[m] is the p×p identity matrix.
- OrthogonalMatrixQ works for symbolic as well as numerical matrices.
- The following options can be given:
-
Normalized True test if matrix columns are normalized SameTest Automatic function to test equality of expressions Tolerance Automatic tolerance for approximate numbers - For exact and symbolic matrices, the option SameTest->f indicates that two entries aij and bij are taken to be equal if f[aij,bij] gives True.
- For approximate matrices, the option Tolerance->t can be used to indicate that the norm γ=m.mT-In∞ satisfying γ≤t is taken to be zero where In is the identity matrix.
Examples
open all close allBasic Examples (2)
Test if a 2×2 numeric matrix is orthogonal:
OrthogonalMatrixQ[(1/Sqrt[2])(| | |
| - | -- |
| 1 | -1 |
| 1 | 1 |)]Test if a 3×3 symbolic matrix is orthogonal:
m = (| | | |
| - | ------ | ------- |
| 1 | 0 | 0 |
| 0 | Cos[α] | -Sin[α] |
| 0 | Sin[α] | Cos[α] |);OrthogonalMatrixQ[m]Transpose[m].m == IdentityMatrix[3]//SimplifyScope (14)
Basic Uses (6)
Test if a real matrix is orthogonal:
m = (1/Sqrt[5]){{1, 2}, {-2, 1}};OrthogonalMatrixQ[m]A real orthogonal matrix is also unitary:
UnitaryMatrixQ[m]Test if a complex matrix is orthogonal:
m = (1/Sqrt[3]){{2, -I}, {I, 2}};OrthogonalMatrixQ[m]m.m == IdentityMatrix[2]A complex-valued orthogonal matrix is not unitary:
UnitaryMatrixQ[m]Test if an exact matrix is orthogonal:
m = (| | | |
| - | -- | -- |
| 4 | -5 | 2 |
| 3 | -3 | -3 |
| 5 | 5 | 5 |);OrthogonalMatrixQ[m]OrthogonalMatrixQ[Orthogonalize[m]]Use OrthogonalMatrixQ with arbitrary-precision matrix:
m = RandomReal[5, {3, 3}, WorkingPrecision -> 15]A random matrix is typically not orthogonal:
OrthogonalMatrixQ[m]Use OrthogonalMatrixQ with a symbolic matrix:
OrthogonalMatrixQ[{{a, b}, {c, d}} / Sqrt[a^2 + b^2]]The matrix becomes orthogonal when
and
:
Block[{c = b, d = -a}, OrthogonalMatrixQ[{{a, b}, {c, d}} / Sqrt[a^2 + b^2]]]OrthogonalMatrixQ works efficiently with large numerical matrices:
m = RandomReal[1, {1000, 1000}];AbsoluteTiming[OrthogonalMatrixQ[m]]a = Orthogonalize[m];
AbsoluteTiming[OrthogonalMatrixQ[a]]Special Matrices (4)
Use OrthogonalMatrixQ with sparse matrices:
SparseArray[{Band[{1, 1}] -> -1}, {5, 5}]OrthogonalMatrixQ[%]Use OrthogonalMatrixQ with structured matrices:
SymmetrizedArray[{{1, 1} -> (1/Sqrt[2]), {1, 2} -> (1/Sqrt[2]), {2, 2} -> -(1/Sqrt[2])}, {2, 2}, Symmetric[All]]OrthogonalMatrixQ[%]The identity matrix is orthogonal:
OrthogonalMatrixQ[IdentityMatrix[3]]HilbertMatrix is not orthogonal:
OrthogonalMatrixQ[HilbertMatrix[5]]Rectangular Semi-orthogonal Matrices (4)
Test if a rectangular matrix is semi-orthogonal:
m = (1/2)(| | | | |
| -- | - | - | -- |
| 1 | 1 | 1 | -1 |
| -1 | 1 | 1 | 1 |);OrthogonalMatrixQ[m]As there are more columns than rows, this indicates that the rows are orthonormal:
m.ConjugateTranspose[m]The columns are not orthonormal:
ConjugateTranspose[m].mTest a matrix with more rows than columns:
m = (1/2)(| | |
| -- | -- |
| 1 | -1 |
| 1 | 1 |
| 1 | 1 |
| -1 | 1 |);OrthogonalMatrixQ[m]The columns of the matrix are orthonormal:
ConjugateTranspose[m].mm.ConjugateTranspose[m]Generate a random orthogonal matrix:
m = RandomVariate[CircularRealMatrixDistribution[4]];OrthogonalMatrixQ[m]Any subset of its rows forms a rectangular semi-orthogonal matrix:
OrthogonalMatrixQ[m[[RandomSample[Range[4], 2]]]]As does any subset of its columns:
OrthogonalMatrixQ[m[[All, RandomSample[Range[4], 2]]]]Rectangular identity matrices are semi-orthogonal:
OrthogonalMatrixQ[IdentityMatrix[{3, 4}]]Options (4)
Normalized (2)
Symbolic orthogonal matrix columns are often not normalized to 1:
m = {{a, b}, {b, -a}};
OrthogonalMatrixQ[m]Avoid testing if the columns are normalized:
OrthogonalMatrixQ[m, Normalized -> False]Multiply the second column of an orthogonal matrix by 2:
m = MapAt[2#&, RotationMatrix[π / 4, {1, 0, 1}], {All, 2}]OrthogonalMatrixQ with NormalizedFalse will still give True for m:
OrthogonalMatrixQ[m, Normalized -> False]However, it will not give true for Transpose[m]:
OrthogonalMatrixQ[Transpose[m], Normalized -> False]This is because
is a diagonal matrix, but
is not:
MatrixForm /@ {m.m, m.m}//FullSimplifySameTest (1)
This matrix is orthogonal for a positive real
, but OrthogonalMatrixQ gives False:
m = {{Log[x ^ 2], 1}, {-1, 2Log[x]}} / Sqrt[1 + 4Log[x] ^ 2];OrthogonalMatrixQ[m]Use the option SameTest to get the correct answer:
OrthogonalMatrixQ[m, SameTest -> (Simplify[#1 - #2, x > 0] == 0&)]Tolerance (1)
Generate an orthogonal real-valued matrix with some random perturbation of order 10-13:
SeedRandom[5];n = 3;
q = Orthogonalize[RandomVariate[NormalDistribution[], {n, n}]] + 10 ^ -13 * RandomReal[1, {n, n}];OrthogonalMatrixQ[q]q.q is not exactly zero outside the main diagonal:
q.q//MatrixFormAdjust the option Tolerance for accepting the matrix as orthogonal:
OrthogonalMatrixQ[q, Tolerance -> 10 ^ -12]Tolerance is applied to the following value:
Norm[q.q - IdentityMatrix[3], ∞]Applications (10)
Sources of Orthogonal Matrices (5)
Any orthonormal basis for
forms an orthogonal matrix:
Subscript[e, 1] = {(1/Sqrt[2]), (1/Sqrt[2]), 0};Subscript[e, 2] = {(1/Sqrt[2]), -(1/Sqrt[2]), 0};Subscript[e, 3] = {0, 0, 1};Table[Subscript[e, i].Subscript[e, j], {i, 3}, {j, 3}]Putting the basis vectors in rows of a matrix forms an orthogonal matrix:
OrthogonalMatrixQ[{Subscript[e, 1], Subscript[e, 2], Subscript[e, 3]}]Putting them in columns also gives an orthogonal matrix:
OrthogonalMatrixQ[{Subscript[e, 1], Subscript[e, 2], Subscript[e, 3]}]Orthogonalize applied to real, linearly independent vectors generates an orthogonal matrix:
m = Orthogonalize[RandomReal[1., {5, 5}]];OrthogonalMatrixQ[m]The matrix does not need to be square, in which case the resulting matrix is semi-orthogonal:
m = Orthogonalize[RandomReal[1., {5, 3}]];OrthogonalMatrixQ[m]m = Orthogonalize[RandomReal[1., {3, 5}]];OrthogonalMatrixQ[m]But the starting matrix must have full rank:
m = (| | |
| - | - |
| 1 | 2 |
| 1 | 2 |);MatrixRank[m]OrthogonalMatrixQ[Orthogonalize[m]]Any rotation matrix is orthogonal:
OrthogonalMatrixQ[RotationMatrix[RandomReal[2 Pi]]]w = RandomReal[1., {3}];
OrthogonalMatrixQ[RotationMatrix[RandomReal[2 Pi], w]]u = RandomReal[1., {3}];
OrthogonalMatrixQ[RotationMatrix[RandomReal[2 Pi], {u, w}]]Any permutation matrix is orthogonal:
m = PermutationMatrix[{2, 4, 1, 3}, TargetStructure -> "Dense"]OrthogonalMatrixQ[m]Matrices drawn from CircularRealMatrixDistribution are orthogonal:
OrthogonalMatrixQ /@ RandomVariate[CircularRealMatrixDistribution[3], 10]Uses of Orthogonal Matrices (5)
Orthogonal matrices preserve the standard inner product on
. In other words, if
is orthogonal and
and
are vectors, then
:
o = RotationMatrix[Pi / 3, RandomReal[1, 3]];
{u, v} = RandomReal[1, {2, 3}];
OrthogonalMatrixQ[o] && u.v == (o.u).(o.v)This means the angles between the vectors are unchanged:
VectorAngle[u, v] == VectorAngle[o.u, o.v]Since the norm is derived from the inner product, norms are preserved as well:
Norm[u] == Norm[o.u]Norm[v] == Norm[o.v]Any orthogonal matrix represents a rotation and/or reflection. If the matrix has determinant
, it is a pure rotation. If it the determinant is
, the matrix includes a reflection. Consider the following matrix:
m = (| | |
| ------------------- | -------------------- |
| -0.9980858626557927 | -0.06184343753901693 |
| 0.06184343753901693 | -0.9980858626557927 |);It is orthogonal and has determinant
:
OrthogonalMatrixQ[m] && Det[m] == 1Thus, it is a pure rotation; the Cartesian unit vectors
and
maintain their relative positions:
o = {0, 0};i = UnitVector[1];j = UnitVector[2];
Graphics[{{Blue, {Arrow[{o, m.i}], Dotted, Arrow[{o, i}]}}, {Red, {Arrow[{o, m.j}], Dotted, Arrow[{o, j}]}}}]The following matrix is orthogonal but has determinant
:
m = (| | |
| ------------------- | ------------------- |
| -0.6512037846116245 | -0.7589029127019458 |
| -0.7589029127019458 | 0.6512037846116244 |);OrthogonalMatrixQ[m] && Det[m] == -1Thus, it includes a reflection; the Cartesian unit vectors
and
reverse their relative positions:
Graphics[{{Blue, {Arrow[{o, m.i}], Dotted, Arrow[{o, i}]}}, {Red, {Arrow[{o, m.j}], Dotted, Arrow[{o, j}]}}}]Orthogonal matrices play an important role in many matrix decompositions:
m = RandomReal[{-1., 1.}, {50, 50}];
{q, r} = QRDecomposition[m];
OrthogonalMatrixQ[q]{u, w, v} = SingularValueDecomposition[m];
{OrthogonalMatrixQ[u], OrthogonalMatrixQ[v]}{s, t} = SchurDecomposition[m];
OrthogonalMatrixQ[s]{p, h} = HessenbergDecomposition[m];
OrthogonalMatrixQ[p]The matrix
is always orthogonal for any nonzero real vector
:
n = 5;
Subscript[ℋ, v_] := IdentityMatrix[n] - 2 vv / v.v;
v = RandomReal[1, n];
OrthogonalMatrixQ[Subscript[ℋ, v]]
is called a Householder reflection; as a reflection, its determinant is
:
Det[Subscript[ℋ, v]]It represents a reflection through a plane perpendicular to
, sending
to
:
Subscript[ℋ, v].v == -vAny vector perpendicular to
is unchanged by
:
perp = Block[{w = RandomReal[1, n]}, w - Projection[w, v]];
Subscript[ℋ, v].perp == perpIn matrix computations,
is used to set to zero selected components of a given column vector
:
x = RandomReal[1, n];v = x - x[[1]] / Abs[x[[1]]] Norm[x]UnitVector[n, 1];
Subscript[ℋ, v].{x}//Chop Find the function
satisfying the following differential equation:
(ⅆx/ⅆt) = Overscript[v, ⇀]⨯x, Overscript[v, ⇀] = {2, -1, 1}, x(0) = {1, 0, -1};Represent the cross-product with
by means of multiplication by the antisymmetric matrix
:
vvec = {2, -1, 1};
(v = -LeviCivitaTensor[3].vvec)//MatrixFormAntisymmetricMatrixQ[v]v.{Subscript[x, 1], Subscript[x, 2], Subscript[x, 3]} == vvec⨯{Subscript[x, 1], Subscript[x, 2], Subscript[x, 3]}Compute the exponential
and use it to define a solution to the equation:
u[t_] := MatrixExp[v t]
x0 = {1, 0, -1};
x[t_] = u[t].x0Verify that
satisfies the differential equation and initial condition:
x'[t] == v.x[t] && x[0] == x0//SimplifyThe matrix
is orthogonal for all values of
:
OrthogonalMatrixQ[u[t]]Thus, the orbit of the solution is at a constant distance from the origin, in this case a circle:
Show[ParametricPlot3D[x[t], {t, 0., 5.}, PlotStyle -> Tube[0.02]], Graphics3D[{Opacity[.5], Sphere[{0, 0, 0}, Norm[x0]]}], PlotRange -> All]Properties & Relations (14)
A matrix is orthogonal if m.Transpose[m]IdentityMatrix[n]:
m = {{Cos[α], -Sin[α]}, {Sin[α], Cos[α]}};{OrthogonalMatrixQ[m], m.m//Simplify}For an approximate matrix, the identity is approximately true:
m = RandomVariate[CircularRealMatrixDistribution[3]];{OrthogonalMatrixQ[m], Norm[m.m - IdentityMatrix[3]]}The inverse of an orthogonal matrix is its transpose:
o = RandomVariate[CircularRealMatrixDistribution[3]];Inverse[o] == Transpose[o]Thus, the inverse and transpose are orthogonal matrices as well:
{OrthogonalMatrixQ[Inverse[o]], OrthogonalMatrixQ[Transpose[o]]}A real orthogonal matrix preserves the standard inner product of vectors in
:
o = RandomVariate[CircularRealMatrixDistribution[4]];
{u, v} = RandomReal[1, {2, 4}];
OrthogonalMatrixQ[o] && u.v == (o.u).(o.v)As a consequence, real orthogonal matrices preserve norms as well:
Norm[u] == Norm[o.u]Norm[v] == Norm[o.v]Any real-valued orthogonal matrix is unitary:
m = Orthogonalize[RandomReal[1, {3, 3}]];{OrthogonalMatrixQ[m], UnitaryMatrixQ[m]}But a complex unitary matrix is typically not orthogonal:
m = Orthogonalize[RandomComplex[1 + I, {3, 3}]];{OrthogonalMatrixQ[m], UnitaryMatrixQ[m]}Products of orthogonal matrices are orthogonal:
{m1, m2} = RandomVariate[CircularRealMatrixDistribution[3], 2];
{OrthogonalMatrixQ[m1], OrthogonalMatrixQ[m2]}OrthogonalMatrixQ[m1.m2]A real-valued orthogonal matrix is normal:
m = Orthogonalize[RandomReal[1, {3, 3}]];{OrthogonalMatrixQ[m], NormalMatrixQ[m]}A complex-valued orthogonal matrix need not be normal:
c = (1/Sqrt[-1 - 2I])(| | |
| ----- | ----- |
| I - 1 | I |
| I | 1 - I |);{OrthogonalMatrixQ[c], NormalMatrixQ[c]}Real-valued orthogonal matrices have eigenvalues that lie on the unit circle:
m = RandomVariate[CircularRealMatrixDistribution[3]];OrthogonalMatrixQ[m]Use Eigenvalues to find eigenvalues:
Eigenvalues[m]Verify they lie on the unit circle:
Abs[%]This does not apply to complex-valued orthogonal matrices:
c = (1/Sqrt[3]){{2, -I}, {I, 2}};
OrthogonalMatrixQ[c]Eigenvalues[c]Real orthogonal matrices have a complete set of eigenvectors:
m = RandomVariate[CircularRealMatrixDistribution[3]];OrthogonalMatrixQ[m]As a consequence, they must be diagonalizable:
DiagonalizableMatrixQ[m]Use Eigenvectors to find eigenvectors:
Eigenvectors[m]A complex orthogonal matrix can fail to be diagonalizable:
c = (| | | |
| ----- | ------ | ----- |
| 1 + I | -1 + I | -1 |
| 1 - I | 1 | 1 + I |
| -1 | -1 - I | 1 - I |);{OrthogonalMatrixQ[c], DiagonalizableMatrixQ[c]}The singular values are all 1 for a real orthogonal matrix:
m = Orthogonalize[RandomReal[1, {3, 3}]];OrthogonalMatrixQ[m]SingularValueList[m]This need not be true for a complex orthogonal matrix:
c = (1/5Sqrt[3])(| | |
| ------ | ------ |
| 4 - 2I | 8 + I |
| -8 - I | 4 - 2I |);OrthogonalMatrixQ[c]SingularValueList[c]The determinant of an orthogonal matrix is 1 or
:
m = RandomVariate[CircularRealMatrixDistribution[3]];{OrthogonalMatrixQ[m], RealAbs[Det[m]]}The 2-norm of a real orthogonal matrix is always 1:
m = Orthogonalize[RandomReal[1, {3, 3}]];{OrthogonalMatrixQ[m], Norm[m]}This need not be true for complex orthogonal matrices:
c = (1/5Sqrt[3])(| | |
| -------- | ------- |
| 8 + I | 4 - 2 I |
| -4 + 2 I | 8 + 1I |);{OrthogonalMatrixQ[c], Norm[c]}Integer powers of orthogonal matrices are orthogonal:
m = RandomVariate[CircularRealMatrixDistribution[3]];OrthogonalMatrixQ[m]UnitaryMatrixQ[MatrixPower[m, RandomInteger[{-10, 10}]]]MatrixExp[m] for real antisymmetric m is both orthogonal and unitary:
m = Symmetrize[RandomReal[1, {5, 5}], Antisymmetric[{1, 2}]];
expm = MatrixExp[m];{OrthogonalMatrixQ[expm], UnitaryMatrixQ[expm]}For complex antisymmetric m, the exponential is orthogonal but not, in general, unitary:
mc = Symmetrize[RandomComplex[1 + I, {5, 5}], Antisymmetric[{1, 2}]];
expmc = MatrixExp[mc];{OrthogonalMatrixQ[expmc], UnitaryMatrixQ[expmc]}OrthogonalMatrix can be used to explicitly construct orthogonal matrices:
OrthogonalMatrix[RandomVariate[CircularRealMatrixDistribution[3]]]These satisfy OrthogonalMatrixQ:
OrthogonalMatrixQ[%]Possible Issues (1)
OrthogonalMatrixQ uses the definition
for both real- and complex-valued matrices:
c = (1/Sqrt[-1 - 8 I])(| | |
| -------- | -------- |
| I | -2 + 2 I |
| -2 + 2 I | -I |);{OrthogonalMatrixQ[c] , c.c == IdentityMatrix[2]}These complex matrices need not be normal or possess many properties of real orthogonal matrices:
NormalMatrixQ[c]UnitaryMatrixQ tests the more common definition
that ensures a complex matrix is normal:
UnitaryMatrixQ[c]Alternatively, test if the entries are real to restrict to real orthogonal matrices:
orthogonalMatrixQ[m_] := OrthogonalMatrixQ[m] && Element[m, Reals]orthogonalMatrixQ[c]Neat Examples (1)
Rotation matrices are orthogonal:
cow = ExampleData[{"Geometry3D", "Cow"}, "GraphicsComplex"];
p = {0, 0, -0.25161901116371155};Table[OrthogonalMatrixQ[RotationMatrix[k Pi / 4., {0, 0, 1}]], {k, -1, 1}]Graphics3D[{EdgeForm[None], Opacity[0.5], Table[{Lighter[ColorData[97, k + 2]], GeometricTransformation[cow, {RotationMatrix[k Pi / 4., {0, 0, 1}], p}]}, {k, -1, 1}]}, Lighting -> "Neutral", ImageSize -> Large, Boxed -> False]Related Guides
History
Text
Wolfram Research (2014), OrthogonalMatrixQ, Wolfram Language function, https://reference.wolfram.com/language/ref/OrthogonalMatrixQ.html.
CMS
Wolfram Language. 2014. "OrthogonalMatrixQ." Wolfram Language & System Documentation Center. Wolfram Research. https://reference.wolfram.com/language/ref/OrthogonalMatrixQ.html.
APA
Wolfram Language. (2014). OrthogonalMatrixQ. Wolfram Language & System Documentation Center. Retrieved from https://reference.wolfram.com/language/ref/OrthogonalMatrixQ.html
BibTeX
@misc{reference.wolfram_2026_orthogonalmatrixq, author="Wolfram Research", title="{OrthogonalMatrixQ}", year="2014", howpublished="\url{https://reference.wolfram.com/language/ref/OrthogonalMatrixQ.html}", note=[Accessed: 12-June-2026]}
BibLaTeX
@online{reference.wolfram_2026_orthogonalmatrixq, organization={Wolfram Research}, title={OrthogonalMatrixQ}, year={2014}, url={https://reference.wolfram.com/language/ref/OrthogonalMatrixQ.html}, note=[Accessed: 12-June-2026]}