Matrix Multiplication
Matrix multiplication is different from element-wise multiplication. Think of it like combining transformations - rotating then scaling is different from scaling then rotating.
The @ Operator
The @ operator is the modern way to multiply matrices.
import numpy as np
a = np.array([[1, 2], [3, 4]])
b = np.array([[5, 6], [7, 8]])
result = a @ b
print(f"Matrix A:\n{a}")
print(f"Matrix B:\n{b}")
print(f"A @ B:\n{result}")
For matrix multiplication, columns of A must equal rows of B. That's why both are 2x2 here.
Shape Rules
If A is (m x n) and B is (n x p), result is (m x p).
import numpy as np
a = np.array([[1, 2, 3], [4, 5, 6]])
b = np.array([[7, 8], [9, 10], [11, 12]])
result = a @ b
print(f"A shape: {a.shape}")
print(f"B shape: {b.shape}")
print(f"Result shape: {result.shape}")
Here is the thing - (2x3) @ (3x2) gives (2x2). The inner dimensions (3) must match.
np.matmul Alternative
np.matmul() does the same thing as @.
import numpy as np
a = np.array([[1, 2], [3, 4]])
b = np.array([[5, 6], [7, 8]])
result1 = a @ b
result2 = np.matmul(a, b)
print(f"Same result: {np.array_equal(result1, result2)}")
One thing that confused me at first was np.dot vs @. For 2D arrays, they do the same thing. But for higher dimensions, behavior differs.
Try it Yourself →Key Takeaways
- The @ operator performs matrix multiplication
- Columns of A must equal rows of B
- Result shape is (rows of A) x (columns of B)
- np.matmul() is equivalent to @ for 2D arrays