II.4 · Linear Algebra
How much do two directions agree?
Turn two vectors and inspect the sign of their dot product. Component multiplication and an angle describe the same alignment, while the parallel part previews projection.
Turn two vectors; read their alignment
A positive dot product means an acute angle: the directions partly agree.
- first direction
- (3, 0)
- second vector
- (2, 2)
- signed component along u
- 6 / (3)2
- dot product
- 6
- first component product
- 6
- second component product
- 0
- angle in radians
- 0.785398
- normalized alignment
- 0.707107
Exact expressions use =. Rounded computations use ≈. All arrows use these same quantities.
A positive dot product means an acute angle: the directions partly agree.
from −4 to 4, up to 2 decimal places
from −4 to 4, up to 2 decimal places
from −4 to 4, up to 2 decimal places
from −4 to 4, up to 2 decimal places
Start with the worked pair and predict the sign after a quarter-turn of . Keep turning until it points against . Choose Perpendicular, then Zero vector, and compare the two states: both have dot product zero, but only one has a defined right angle.
Intuition: alignment with size
Two equally directed vectors reinforce the same move. Perpendicular vectors share no component along each other’s direction. Opposite vectors disagree. The dot product encodes this with a positive value, zero, or a negative value. It also depends on length: doubling either vector doubles the product, even if the angle stays unchanged.
The parallel arrow in the stage shows the part of along the line of . Its signed scalar component is positive on ‘s ray and negative on the opposite ray. Multiplying that scalar component by gives the dot product. The complete decomposition is the subject of II.5 Projection.
Definition
For ,
The output is a scalar, not a vector. If both vectors are nonzero and is their smaller, unsigned angle,
Angles are in radians. The two vectors are orthogonal when their dot product is zero. For nonzero vectors this means perpendicular directions and . The zero vector is algebraically orthogonal to every vector, but it has no direction and forms no defined angle.
Mechanics: products before the sum
The inspector separates and . Either product may be negative; their sum determines alignment. In the perpendicular preset and , both products vanish. For and , they instead cancel as . Perpendicularity does not require axis alignment or a zero component.
For nonzero vectors, a positive product means an angle below ; a negative product means an angle above . At identical directions , and at opposite directions . The arc always represents this smaller angle, rather than a directed full rotation. Turning clockwise and counter-clockwise to the same endpoint can therefore give the same angle.
Derivation: components meet geometry
Form the triangle with sides , , and the vector between their tips. Expand the squared length of that last side:
The cosine rule for the same triangle gives
Equating the final terms proves the geometric identity. Symmetry follows directly from multiplication of real numbers: . Distributivity gives . Finally, .
The geometric identity also implies , since . This bound explains the legal range of a computed cosine.
Worked examples
For and , the product is . Their lengths are and , so and . Inspect the arithmetic before the angular interpretation.
Inspect the worked calculation
For u = (3, 0) and v = (2, 2), multiply matching components: 6 + 0 = 6.
- first direction
- (3, 0)
- second vector
- (2, 2)
- signed component along u
- 6 / (3)2
- dot product
- 6
- first component product
- 6
- second component product
- 0
- angle in radians
- 0.785398
- normalized alignment
- 0.707107
For and , the dot product is : the angle is acute even though one matching-component product is negative. For and , the product is and the angle is . These cases separate the sign of one component from the sign of overall alignment.
Executable reference code
The pedagogical dot product interprets decimal components exactly. Its angle routine first normalizes rescaled finite vectors and then checks the cosine range. NumPy’s on two one-dimensional arrays computes their dot product; the remaining lines expose the angle calculation and the zero checks.
from fractions import Fraction
from math import acos, hypot, isfinite, ulp
def dot(u, v):
if len(u) != 2 or len(v) != 2:
raise ValueError('Expected two components per vector')
return sum(Fraction(str(x)) * Fraction(str(y)) for x, y in zip(u, v))
def angle(u, v):
directions = []
for w in (u, v):
if len(w) != 2 or not all(isfinite(x) for x in w):
raise ValueError('Expected finite two-component vectors')
m = max(map(abs, w))
if m == 0:
raise ValueError('An angle requires two nonzero vectors')
w = tuple(x / m for x in w)
h = hypot(*w)
directions.append(tuple(x / h for x in w))
cosine = sum(x*y for x, y in zip(*directions))
if not isfinite(cosine) or abs(cosine) > 1 + 8 * ulp(1.0):
raise ArithmeticError('Invalid cosine; clipping would hide an error')
return acos(max(-1.0, min(1.0, cosine)))
if __name__ == '__main__':
assert dot((2, 1), (-1, 2)) == 0
assert dot((2, -1), (3, 4)) == 2import numpy as np
u = np.array([3.0, 0.0])
v = np.array([2.0, 2.0])
product = u @ v
# Rescale each vector before normalizing, avoiding squared-norm overflow.
if not np.isfinite(u).all() or not np.isfinite(v).all():
raise ValueError('Finite components required')
mu, mv = np.max(np.abs(u)), np.max(np.abs(v))
if mu == 0 or mv == 0:
raise ValueError('Angle undefined at zero')
un, vn = u / mu, v / mv
un, vn = un / np.hypot(*un), vn / np.hypot(*vn)
cosine = float(un @ vn)
if not np.isfinite(cosine) or abs(cosine) > 1 + 8 * np.finfo(float).eps:
raise ArithmeticError('Invalid cosine; do not conceal it with clipping')
angle = np.arccos(np.clip(cosine, -1, 1))
assert product == 6
assert np.isclose(angle, np.pi / 4)Explore
With , construct a perpendicular vector by solving . Compare and : the angle agrees, although their lengths differ. Now scale a nonperpendicular vector by : predict the changed dot product and unchanged cosine. Scale by : the dot product changes sign and the angle becomes .
Common mistakes
Multiplying component sums, , introduces cross terms and is not a dot product. Treating zero product as proof of a right angle overlooks zero vectors. A large positive product also does not necessarily mean a smaller angle than a smaller product: different vector lengths can dominate the comparison. Normalized alignment removes that size dependence.
Numerical considerations
Computing requires two nonzero vectors and finite, valid arithmetic. Normalizing after rescaling avoids intermediate squared-norm overflow. A rounded cosine can land a few ulps outside . The code allows at most eight binary64 epsilon units beyond an endpoint, reflecting the rounding of the normalized products and their sum. Values such as , infinity, or NaN are rejected; unrestricted clipping would hide an invalid computation.
Near parallel directions, is sensitive because cosine changes very slowly with angle. The stage retains an exact decimal cross product and evaluates the equivalent smaller angle . This preserves a small angle that might be lost by rounding cosine to . Exact decimal orthogonality in the stage uses no tolerance; measured floating-point vectors require a comparison scaled to their magnitudes and measurement uncertainty.
Engineering and ML connections
Work done by a force along a displacement is a dot product: perpendicular force contributes no work along that move. A weighted feature score also multiplies matching coordinates and sums them. Cosine similarity compares normalized alignment, so it is undefined for a zero input unless an application declares a separate convention. Two-dimensional geometry supplies the mental model; the matching-component sum extends to longer vectors.
Exercises
Summary and checkpoints
A dot product is both a matching-component sum and length-weighted alignment. Check that you can predict its sign, construct perpendicular vectors, distinguish algebraic orthogonality from a right angle at zero, and explain the narrow clipping policy. The next chapter turns the parallel component into a complete projection-and-residual decomposition.