Skip to content

Rotations

§3.4 established that orthogonal matrices preserve every length and every angle. That is a strong property, and it leaves exactly two kinds of map: those that preserve orientation and those that reverse it. The first kind are rotations.

They are the transformations that move data without distorting any of the geometry this chapter built — which makes them the right tool whenever you want to change coordinates without changing what the data means. Every U\mathbf{U} and V\mathbf{V} in a singular value decomposition is one, which is why Chapter 4’s factorisation reads as “rotate, scale, rotate”.

  • What a rotation is, and why detR=+1\det \mathbf{R} = +1 is the extra condition beyond orthogonality.
  • The 2×22\times2 rotation matrix, derived from where it sends the standard basis.
  • The three 3×33\times3 rotations about the coordinate axes (Equations 3.77 to 3.79) and the convention that fixes their signs.
  • Givens rotations (Definition 3.11): rotation in one plane of Rn\mathbb{R}^n, leaving everything else alone.
  • The four properties of §3.9.4 — including the measured failure of commutativity in three dimensions.
  • Why composing a hundred thousand rotations drifts, and by how much.

Intuition: turning the page, not stretching it

Section titled “Intuition: turning the page, not stretching it”

Put a photograph on a table and turn it. Nothing about the photograph changes: no distance between two printed points changes, no angle changes, nothing is stretched or mirrored. Only the orientation relative to the table changed, and the table’s origin stayed put.

That is a rotation. Contrast it with three neighbours:

operationpreserves lengths?preserves angles?preserves orientation?
rotationyesyesyes
reflectionyesyesno
uniform scalingnoyesyes
shearnonoyes

Rotations are the intersection of the first two columns and the third. Orthogonality buys the first two; det=+1\det = +1 buys the third.

diagram Diagram mermaid

Note “automorphism”: a rotation maps the space onto itself bijectively. It cannot flatten anything, which the determinant being nonzero already guarantees.

Fix the standard basis {e1,e2}\{\mathbf{e}_1, \mathbf{e}_2\} and ask where a rotation by θ\theta sends each basis vector. Trigonometry on the unit circle gives

Φ(e1)=[cosθsinθ],Φ(e2)=[sinθcosθ](3.75)\Phi(\mathbf{e}_1) = \begin{bmatrix}\cos\theta\\ \sin\theta\end{bmatrix}, \qquad \Phi(\mathbf{e}_2) = \begin{bmatrix}-\sin\theta\\ \cos\theta\end{bmatrix} \tag{3.75}

and since the columns of a matrix are the images of the basis vectors (Chapter 2, §2.7),

R(θ)=[Φ(e1)Φ(e2)]=[cosθsinθsinθcosθ](3.76)\mathbf{R}(\theta) = \begin{bmatrix}\Phi(\mathbf{e}_1) & \Phi(\mathbf{e}_2)\end{bmatrix} = \begin{bmatrix}\cos\theta & -\sin\theta\\ \sin\theta & \cos\theta\end{bmatrix} \tag{3.76}

That is the entire derivation. There is nothing to memorise beyond “where does e1\mathbf{e}_1 go” — the minus sign sits in the top right because e2\mathbf{e}_2 swings backwards into the second quadrant.

Two facts fall out. R(θ)R(θ)=I\mathbf{R}(\theta)^\top\mathbf{R}(\theta) = \mathbf{I} because cos2+sin2=1\cos^2 + \sin^2 = 1, and detR(θ)=cos2θ+sin2θ=1\det\mathbf{R}(\theta) = \cos^2\theta + \sin^2\theta = 1 exactly. And the composition rule is addition of angles: R(α)R(β)=R(α+β)\mathbf{R}(\alpha)\mathbf{R}(\beta) = \mathbf{R}(\alpha+\beta), which is the angle-sum identity written as a matrix product.

In the plane there is one plane to rotate. In space you must say which plane, and the standard choice is to name the axis left fixed. The convention: “counterclockwise” about an axis means looking at that axis head on, from its tip toward the origin.

R1(θ)=[1000cosθsinθ0sinθcosθ](3.77)\mathbf{R}_1(\theta) = \begin{bmatrix}1 & 0 & 0\\ 0 & \cos\theta & -\sin\theta\\ 0 & \sin\theta & \cos\theta\end{bmatrix} \tag{3.77} R2(θ)=[cosθ0sinθ010sinθ0cosθ](3.78)\mathbf{R}_2(\theta) = \begin{bmatrix}\cos\theta & 0 & \sin\theta\\ 0 & 1 & 0\\ -\sin\theta & 0 & \cos\theta\end{bmatrix} \tag{3.78} R3(θ)=[cosθsinθ0sinθcosθ0001](3.79)\mathbf{R}_3(\theta) = \begin{bmatrix}\cos\theta & -\sin\theta & 0\\ \sin\theta & \cos\theta & 0\\ 0 & 0 & 1\end{bmatrix} \tag{3.79}

R1\mathbf{R}_1 fixes the e1\mathbf{e}_1 coordinate and rotates the e2e3\mathbf{e}_2\mathbf{e}_3 plane; R3\mathbf{R}_3 fixes e3\mathbf{e}_3 and is the 2×22\times2 case padded out. R2\mathbf{R}_2 has its signs the other way round+sin+\sin in the top right — and that is not a typo: it follows from the head-on-from-the-tip convention applied to the e1e3\mathbf{e}_1\mathbf{e}_3 plane, which the book spells out. If you write R2\mathbf{R}_2 from pattern-matching rather than from the convention you will get it backwards, and the resulting bug rotates the right amount in the wrong direction.

Equation 3.80 looks forbidding and says something simple: take the identity, and change four entries. A Givens rotation fixes n2n-2 dimensions and rotates the remaining two-dimensional plane. It is how you rotate in high dimensions at all, and it is how numerical routines zero out matrix entries one at a time — Givens QR does exactly that.

The parameter count follows: choosing the plane means choosing {i,j}\{i, j\}, so a general rotation in Rn\mathbb{R}^n needs (n2)=n(n1)/2\binom{n}{2} = n(n-1)/2 angles. That is 11 in the plane, 33 in space, 66 in R4\mathbb{R}^4 and 4545 in R10\mathbb{R}^{10} — so “one angle” is a coincidence of two dimensions, not the general rule.

The first two are §3.4’s Equations 3.31 and 3.32, since a rotation is an orthogonal matrix. The third is the one that costs people real time, and it is worth measuring rather than accepting.

The book’s Exercise 3.10 — rotate by 30 degrees

Section titled “The book’s Exercise 3.10 — rotate by 30 degrees”

cos30°=320.866025\cos 30° = \tfrac{\sqrt{3}}{2} \approx 0.866025 and sin30°=12\sin 30° = \tfrac{1}{2}, so

R(30°)=[32121232][0.8660250.50.50.866025]\mathbf{R}(30°) = \begin{bmatrix}\tfrac{\sqrt3}{2} & -\tfrac12\\[2pt] \tfrac12 & \tfrac{\sqrt3}{2}\end{bmatrix} \approx \begin{bmatrix}0.866025 & -0.5\\ 0.5 & 0.866025\end{bmatrix}

x1=(2,3)\mathbf{x}_1 = (2,3)^\top:

Rx1=[232312212+332]=[3321+332][0.2320513.598076]\mathbf{R}\mathbf{x}_1 = \begin{bmatrix}2\cdot\tfrac{\sqrt3}{2} - 3\cdot\tfrac12\\[2pt] 2\cdot\tfrac12 + 3\cdot\tfrac{\sqrt3}{2}\end{bmatrix} = \begin{bmatrix}\sqrt3 - \tfrac32\\[2pt] 1 + \tfrac{3\sqrt3}{2}\end{bmatrix} \approx \begin{bmatrix}0.232051\\ 3.598076\end{bmatrix}

x2=(0,1)\mathbf{x}_2 = (0,-1)^\top:

Rx2=[0+12032]=[1232]=[0.50.866025]\mathbf{R}\mathbf{x}_2 = \begin{bmatrix}0 + \tfrac12\\[2pt] 0 - \tfrac{\sqrt3}{2}\end{bmatrix} = \begin{bmatrix}\tfrac12\\[2pt] -\tfrac{\sqrt3}{2}\end{bmatrix} = \begin{bmatrix}0.5\\ -0.866025\end{bmatrix}

Note that Rx2\mathbf{R}\mathbf{x}_2 is e2-\mathbf{e}_2 rotated by 30°30°, which is e1\mathbf{e}_1 rotated by 60°-60° — the second column of R\mathbf{R}, negated. Rotating a basis vector just reads off a column.

The checks:

quantitybeforeafter
x1\lVert\mathbf{x}_1\rVert13=3.605551\sqrt{13} = 3.6055513.6055513.605551
x2\lVert\mathbf{x}_2\rVert1.0000001.0000001.0000001.000000
angle between them146.309932°146.309932°146.309932°146.309932°
detR\det\mathbf{R}1.0000000000000001.000000000000000

Nine matching digits on the angle, and the determinant is exactly 11 in floating point.

The book’s Figure 3.14, and a lesson about rounding

Section titled “The book’s Figure 3.14, and a lesson about rounding”

The book’s opening example gives

R=[0.380.920.920.38](3.74)\mathbf{R} = \begin{bmatrix}-0.38 & -0.92\\ 0.92 & -0.38\end{bmatrix} \tag{3.74}

and captions the figure “Rotated by 112.5°112.5°”. Check it: arctan2(0.92, 0.38)=112.4428°\arctan2(0.92,\ -0.38) = 112.4428°, which is close to 112.5°112.5° but not equal, and

detR=(0.38)2+(0.92)2=0.1444+0.8464=0.99081.\det\mathbf{R} = (-0.38)^2 + (0.92)^2 = 0.1444 + 0.8464 = 0.9908 \neq 1 .

The matrix as printed is not orthogonal: RRI=0.0130\lVert\mathbf{R}^\top\mathbf{R} - \mathbf{I}\rVert = 0.0130. The reason is benign — the book rounded cos112.5°=0.382683\cos 112.5° = -0.382683 and sin112.5°=0.923880\sin 112.5° = 0.923880 to two decimals for readability — but the lesson generalises. A rounded rotation matrix is not a rotation matrix. It shrinks every vector it touches by about 0.5%0.5\% here, and if you compose a few hundred of them the drift compounds. This is why graphics and robotics code re-orthonormalises stored rotations periodically, and why quaternions (which need only be renormalised, one division) are popular for storing orientations.

rotations_worked.py
import numpy as np
 
def R2(theta):
    c, s = np.cos(theta), np.sin(theta)
    return np.array([[c, -s], [s, c]])
 
R = R2(np.radians(30.0))
print("R(30) =\n", np.round(R, 6))
 
cos = lambda a, b: float(a @ b) / (np.linalg.norm(a) * np.linalg.norm(b))
x1, x2 = np.array([2.0, 3.0]), np.array([0.0, -1.0])
y1, y2 = R @ x1, R @ x2
print("x1 ->", np.round(y1, 6), "  exact:", round(np.sqrt(3) - 1.5, 6), round(1 + 1.5 * np.sqrt(3), 6))
print("x2 ->", np.round(y2, 6), "  exact:", 0.5, round(-np.sqrt(3) / 2, 6))
print("lengths:", round(float(np.linalg.norm(x1)), 6), "->", round(float(np.linalg.norm(y1)), 6))
print("angle before:", round(float(np.degrees(np.arccos(np.clip(cos(x1, x2), -1, 1)))), 6))
print("angle after: ", round(float(np.degrees(np.arccos(np.clip(cos(y1, y2), -1, 1)))), 6))
print("det R =", f"{np.linalg.det(R):.15f}")
 
# The book's Equation 3.74, as printed.
Rb = np.array([[-0.38, -0.92], [0.92, -0.38]])
print()
print("Eq 3.74 det =", round(float(np.linalg.det(Rb)), 6))
print("||Rb^T Rb - I|| =", f"{np.linalg.norm(Rb.T @ Rb - np.eye(2)):.4f}")
print("its angle:", round(float(np.degrees(np.arctan2(0.92, -0.38))), 4), "deg")
print("exact cos(112.5) =", round(float(np.cos(np.radians(112.5))), 6),
      " sin(112.5) =", round(float(np.sin(np.radians(112.5))), 6))
output
R(30) =
 [[ 0.866025 -0.5     ]
 [ 0.5       0.866025]]
x1 -> [0.232051 3.598076]   exact: 0.232051 3.598076
x2 -> [ 0.5      -0.866025]   exact: 0.5 -0.866025
lengths: 3.605551 -> 3.605551
angle before: 146.309932
angle after:  146.309932
det R = 1.000000000000000
 
Eq 3.74 det = 0.9908
||Rb^T Rb - I|| = 0.0130
its angle: 112.4428 deg
exact cos(112.5) = -0.382683  sin(112.5) = 0.92388

The first sketch is Equation 3.76 with the matrix on screen and both preservation properties measured live.

sketch R(theta) turns and never distorts p5.js
Drag theta. The shape rotates, the live matrix updates, and the two readouts measure the largest change in any pairwise distance and the change in the angle between two marked vertices. Both stay at machine epsilon for every theta, which is Equations 3.31 and 3.32 checked continuously.

The second sketch is the non-commutativity, in an oblique three-dimensional view.

sketch In space, the order matters p5.js
Two knobs set the angles of a rotation about e1 and a rotation about e3. The blue outline is R1 then R3 applied to the box, the amber outline is R3 then R1, and the red segments join corresponding corners. Set either angle to zero and the two coincide; set both and they do not. The Frobenius norm of the commutator is measured underneath.

The third sketch shows what a Givens rotation actually is: the identity with four entries changed.

sketch A Givens rotation is the identity with four entries changed p5.js
Pick the plane (i, j) and the angle. The grid is the full n by n matrix, with unchanged identity entries in grey and the four altered entries highlighted. The readout counts how many entries differ from the identity, and confirms the matrix is orthogonal with determinant one for every choice.

And the matrix stepper on a 30°30° rotation, which reports the eigenvalues — a rotation in the plane has no real eigenvectors unless θ\theta is a multiple of π\pi, and that is worth seeing:

matrixR(30 degrees) as a linear maplinear map on R^2
-4-2024-4-2024x1x2
0.87-0.500.500.87
columns of A = images of e1, e2
det A 1.00area factor 1.00orientation preserved
det A1.00A e1(0.87, 0.50)A e2(-0.50, 0.87)
basisThe plane before anything happens, with the standard basis e1 = (1, 0) and e2 = (0, 1) and the unit square they span.
1/8

The lattice turns rigidly. Note that no real direction is preserved: a genuine rotation in the plane has a complex pair of eigenvalues, which is the algebraic statement that it fixes no line.

rotations_from_scratch.py
import numpy as np
 
def rot2(theta):
    c, s = np.cos(theta), np.sin(theta)
    return np.array([[c, -s], [s, c]])
 
def givens(n, i, j, theta):
    """Equation 3.80: the identity with four entries replaced. 1-based i, j."""
    R = np.eye(n)
    c, s = np.cos(theta), np.sin(theta)
    R[i - 1, i - 1] = c
    R[i - 1, j - 1] = -s
    R[j - 1, i - 1] = s
    R[j - 1, j - 1] = c
    return R
 
def axis_rotations(theta):
    """Equations 3.77 to 3.79. Note R2's signs are the other way round."""
    c, s = np.cos(theta), np.sin(theta)
    R1 = np.array([[1, 0, 0], [0, c, -s], [0, s, c]], dtype=float)
    R2 = np.array([[c, 0, s], [0, 1, 0], [-s, 0, c]], dtype=float)
    R3 = np.array([[c, -s, 0], [s, c, 0], [0, 0, 1]], dtype=float)
    return R1, R2, R3
 
# Are they all orthogonal with determinant one?
for name, M in zip(("R1", "R2", "R3"), axis_rotations(0.7)):
    print(f"{name}: det {np.linalg.det(M):.15f}   ||M^T M - I|| {np.linalg.norm(M.T @ M - np.eye(3)):.2e}")
G = givens(6, 2, 5, 0.7)
print("Givens R_25 in R^6: det", f"{np.linalg.det(G):.15f}",
      "  entries differing from I:", int(np.sum(np.abs(G - np.eye(6)) > 1e-12)))
 
# Commutativity: yes in the plane, no in space.
a, b = np.radians(35.0), np.radians(70.0)
print()
print("2-D:  ||R(a)R(b) - R(b)R(a)|| =", f"{np.linalg.norm(rot2(a) @ rot2(b) - rot2(b) @ rot2(a)):.3e}")
print("2-D:  ||R(a)R(b) - R(a+b)||   =", f"{np.linalg.norm(rot2(a) @ rot2(b) - rot2(a + b)):.3e}")
R1a, _, _ = axis_rotations(a)
_, _, R3b = axis_rotations(b)
print("3-D:  ||R1R3 - R3R1||_F       =", round(float(np.linalg.norm(R1a @ R3b - R3b @ R1a)), 6))
 
# How far does orthogonality drift when you compose many rotations?
print()
rng = np.random.default_rng(11)
M = np.eye(3)
for k in range(1, 100001):
    which = k % 3
    R1k, R2k, R3k = axis_rotations(rng.uniform(0, 2 * np.pi))
    M = M @ (R1k if which == 0 else R2k if which == 1 else R3k)
    if k in (10, 100, 1000, 10000, 100000):
        print(f"after {k:6} products: ||M^T M - I|| {np.linalg.norm(M.T @ M - np.eye(3)):.3e}   "
              f"det {np.linalg.det(M):.15f}")
output
R1: det 1.000000000000000   ||M^T M - I|| 2.95e-17
R2: det 1.000000000000000   ||M^T M - I|| 2.95e-17
R3: det 1.000000000000000   ||M^T M - I|| 2.95e-17
Givens R_25 in R^6: det 1.000000000000000   entries differing from I: 4
 
2-D:  ||R(a)R(b) - R(b)R(a)|| = 1.570e-16
2-D:  ||R(a)R(b) - R(a+b)||   = 1.110e-16
3-D:  ||R1R3 - R3R1||_F       = 0.961059
 
after     10 products: ||M^T M - I|| 3.362e-16   det 1.000000000000000
after    100 products: ||M^T M - I|| 1.940e-15   det 1.000000000000000
after   1000 products: ||M^T M - I|| 4.724e-15   det 0.999999999999998
after  10000 products: ||M^T M - I|| 2.482e-14   det 0.999999999999980
after 100000 products: ||M^T M - I|| 2.907e-13   det 0.999999999999751

Three results. The Givens rotation differs from the identity in exactly four entries, as Equation 3.81 says. In the plane the two orders agree to 1.6×10161.6\times10^{-16} and the composition really is the angle sum; in space R1R3R3R1F=0.961059\lVert\mathbf{R}_1\mathbf{R}_3 - \mathbf{R}_3\mathbf{R}_1\rVert_F = 0.961059, which is not a small number.

The drift table is the practical one. Composing 100,000100{,}000 rotations leaves orthogonality off by 2.9×10132.9\times10^{-13} and the determinant off by 2.5×10132.5\times10^{-13}. That is remarkably good — the error grows roughly like k\sqrt{k} rather than like kk, because the individual rounding errors are uncorrelated — and it is still a drift. Long-running simulations that accumulate rotations re-orthonormalise periodically for exactly this reason.

figure Three hundred and sixty rotations, nothing measurable changes matplotlib
Left, a cloud of forty points drawn at four different rotation angles. Right, a log plot of the largest change in any pairwise distance, the largest change in any pairwise angle, and the deviation of the determinant from one, all flat near machine epsilon across three hundred and sixty degrees. Left, a cloud of forty points drawn at four different rotation angles. Right, a log plot of the largest change in any pairwise distance, the largest change in any pairwise angle, and the deviation of the determinant from one, all flat near machine epsilon across three hundred and sixty degrees.
780 pairwise distances and 780 pairwise angles were re-measured at every one of 361 angles. The worst change in any distance over the whole sweep is 1.776e-15 and the worst change in any angle is 1.827e-13, against a machine epsilon of 2.22e-16.
figure Commutativity is a two-dimensional accident matplotlib
Left, a square in the plane with the two composition orders drawn on top of each other and indistinguishable. Right, a three-dimensional plate with the two orders drawn separately and red segments joining corresponding corners, showing a visible gap. Left, a square in the plane with the two composition orders drawn on top of each other and indistinguishable. Right, a three-dimensional plate with the two orders drawn separately and red segments joining corresponding corners, showing a visible gap.
Same two angles, 35 and 70 degrees, applied in both orders. In the plane the largest gap between the two results is 3.14e-16 — machine noise. In space it is 0.743106, and the Frobenius norm of the commutator is 0.961059.

From the preservation plot. Three curves sit flat at the bottom across a full turn. The measured worst cases over the whole sweep are 1.776×10151.776\times10^{-15} for distances and 1.827×10131.827\times10^{-13} for angles, against a machine epsilon of 2.22×10162.22\times10^{-16}. So distances hold to about eight units in the last place and angles to about eight hundred.

Why the difference? The angle goes through arccos, whose derivative blows up near ±1\pm 1 — an argument known to 101610^{-16} gives an angle known to 1016=108\sqrt{10^{-16}} = 10^{-8} in the worst case. The angles here are not near-degenerate so the amplification is only a factor of a few hundred, but the asymmetry between the two curves is a property of arccos rather than of rotations. This is the same sensitivity that makes the clip on the Angles and Orthogonality page mandatory.

From the commutativity figure. The left panel is the control: the two orders in the plane are drawn one on top of the other and you cannot see two outlines, because the largest gap is 3.14×10163.14\times10^{-16}. The right panel uses the same two angles and the gap is 0.7431060.743106 — over a plate whose longest side is 0.80.8, so the two results are nearly a plate-width apart.

The commutator norm R1R3R3R1F=0.961059\lVert\mathbf{R}_1\mathbf{R}_3 - \mathbf{R}_3\mathbf{R}_1\rVert_F = 0.961059 is the measurement to keep. Two rotation matrices, each of Frobenius norm 31.73\sqrt{3} \approx 1.73, whose products in the two orders differ by nearly 11. This is not a small effect to be managed with care; it is the reason Euler angles need a stated convention, the reason “roll, pitch, yaw” is ambiguous without an order, and the reason rotation composition is written down as a group rather than as a sum of angles.

And the group structure is the clean way to say it. In two dimensions R(α)R(β)=R(α+β)\mathbf{R}(\alpha)\mathbf{R}(\beta) = \mathbf{R}(\alpha+\beta), measured to 1.1×10161.1\times10^{-16}: the rotations are just the reals modulo 2π2\pi in disguise, an Abelian group. In three dimensions there is no such parametrisation, and the failure of commutativity is precisely the obstruction.

mapconditionpreservesdeterminantexample
rotationRR=I\mathbf{R}^\top\mathbf{R}=\mathbf{I}, det=+1\det=+1lengths, angles, orientation+1+1R(θ)\mathbf{R}(\theta), Givens, SVD’s U\mathbf{U} and V\mathbf{V}
reflectionRR=I\mathbf{R}^\top\mathbf{R}=\mathbf{I}, det=1\det=-1lengths, angles1-1diag(1,1)\mathrm{diag}(1,-1); Householder
uniform scalingA=cI\mathbf{A}=c\mathbf{I}anglescnc^n2I2\mathbf{I}
general orthogonalRR=I\mathbf{R}^\top\mathbf{R}=\mathbf{I}lengths, angles±1\pm1whatever qr gives you
shearnonearea (if det=1\det=1)11[1101]\begin{bmatrix}1&1\\0&1\end{bmatrix}
projectionP2=P\mathbf{P}^2=\mathbf{P}nothing00 unless P=I\mathbf{P}=\mathbf{I}§3.8

Reading the determinant column: +1+1 is a rotation, 1-1 a reflection, 00 a projection, anything else a scaling of some kind. It is the fastest single diagnostic on an unfamiliar matrix.

pch.quizTag Check your understanding
  1. Orthogonality gives length and angle preservation. What does det R = +1 add?

    pch.quizShowAnswer

    B — Orientation preservation — the other case, det = -1, is a reflection, which preserves every length and every unsigned angle while flipping handedness — Orthogonality forces det(R)^2 = 1, so the determinant is plus or minus one and both occur. diag(1, -1) is orthogonal with determinant -1, and np.linalg.qr returns a determinant of exactly (-1)^(n-1) — so in every even dimension its Q is a reflection, not a rotation.

  2. Why does Equation 3.78 have +sin(theta) in the top right where 3.77 and 3.79 have -sin(theta)?

    pch.quizShowAnswer

    B — It follows from the convention that counterclockwise about an axis means looking at that axis head on from its tip toward the origin — applied to the e1-e3 plane, that convention flips the sign pattern — Writing R2 by pattern-matching the other two gives a rotation by minus theta about e2. The symptom is a system turning the right amount in the wrong direction.

  3. A Givens rotation R_ij(theta) in R^6 differs from the identity in how many entries?

    pch.quizShowAnswer

    B — 4 — Equation 3.81 names them: r_ii = cos, r_ij = -sin, r_ji = sin, r_jj = cos. It fixes the other four dimensions entirely, which is why a general rotation in R^6 needs 15 angles rather than one.

  4. The measured commutator norm for two 3-D axis rotations at 35 and 70 degrees is 0.961. What is the practical consequence?

    pch.quizShowAnswer

    B — Three Euler angles do not determine a rotation without an ordering convention — there are twelve conventional orderings and they give twelve different results from the same three numbers — Each of those matrices has Frobenius norm sqrt(3), so a commutator of 0.961 is not a small perturbation. In the plane the same measurement is 1.6e-16, because two-dimensional rotations are an Abelian group.

  5. Composing 100000 random 3-D rotations leaves ||M-transpose M minus I|| at 2.9e-13. How should that be read?

    pch.quizShowAnswer

    B — Orthogonality is robust but does drift — the error grows roughly like the square root of the number of products, since individual rounding errors are uncorrelated — so long-running accumulations should re-orthonormalise — The determinant also drifts, to 0.999999999999751. Both are small enough to ignore for a hundred products and worth handling for a hundred thousand.

Exercise 2 – Test the book’s Equation 3.74

Section titled “Exercise 2 – Test the book’s Equation 3.74”

Exercise 4 – Commutativity, measured in two dimensions and three

Section titled “Exercise 4 – Commutativity, measured in two dimensions and three”
  • A rotation is an orthogonal matrix with determinant plus one — orthogonality buys length and angle preservation, and the determinant condition adds orientation preservation. Determinant minus one is a reflection.
  • The two-by-two rotation matrix is read off the images of the basis vectors: cosine and sine down the first column, minus sine and cosine down the second.
  • In two dimensions rotations compose by adding angles and they commute, forming an Abelian group.
  • In three dimensions there are three axis rotations, and the middle one has its sine signs reversed because of the look-at-the-axis-from-its-tip convention.
  • A Givens rotation is the identity with four entries changed, rotating one plane and fixing the other n minus two dimensions. A general rotation in n dimensions needs n(n−1)/2 angles.
  • Rotations in three or more dimensions do not commute. Measured on two axis rotations at 35 and 70 degrees, the commutator has Frobenius norm 0.961 and the two orders move a plate’s corners 0.743 apart.
  • Rotations form a group only about a shared fixed point; rotating about any other point is an affine map, the shift-transform-shift-back pattern of section 3.8.4.
  • A rounded rotation matrix is not a rotation. The book’s own Equation 3.74 has determinant 0.9908 and shrinks vectors by about half a percent.
  • Composing a hundred thousand rotations drifts orthogonality to three times ten to the minus thirteen, growing like the square root of the count — negligible for a hundred products, worth correcting for a hundred thousand.

Next: Chapter 3 Exercises and Solutions — all ten of the book’s exercises, worked.

pch.coffeeTagline

pch.coffeeCta

pch.feedbackHeading

pch.feedbackSubheading