Contraction
At a Glance
- Contraction generalizes vector inner products and matrix multiplication to higher dimensions.
- Sums over matching pairs of dimensions between two tensors.
- The fundamental operation for composing tensors in networks and quantum algorithms.
- Contracted dimensions must have matching sizes.
- Result contains only the uncontracted dimensions from both input tensors.
Overview
Tensor contraction is a fundamental operation in multilinear algebra that generalizes familiar operations like vector inner products and matrix multiplication to higher-dimensional arrays. It is the primary way tensors are composed into more complex tensors.
Conceptually, contraction takes two tensors and "contracts" (sums over) one or more pairs of matching dimensions, similar to how matrix multiplication sums over the shared dimension between two matrices. This operation is essential in quantum mechanics, general relativity, and machine learning.
For an introduction to tensors and their properties, see the Tensor concept page.
Mathematical Definition
Given two tensors and , a contraction specifies:
- Which dimensions of to contract (e.g., dimensions )
- Which dimensions of to contract (e.g., dimensions )
The contracted dimensions must have matching sizes. The operation sums over all values in these dimensions, producing a result tensor whose dimensions are the uncontracted dimensions from both inputs.
Formally, for tensors and :
where , , and represent multi-indices for the uncontracted-left, contracted, and uncontracted-right dimensions respectively.
Vector Inner Product as Contraction
The inner product of two vectors is the simplest example of tensor contraction. It takes two order one tensors and contracts their only dimension, producing a scalar.
Mathematical notation:
For vectors :
Code example:
// Vector inner product: contract the single dimension
var u = random_tensor([5],as_complex) // Vector of length 5
var v = random_tensor([5],as_complex) // Vector of length 5
var inner_product = contract_conjugate(u, v, [0], [0])
print(inner_product) // Complex order 0 tensor, a single scalar
Matrix-Matrix Product as Contraction
Matrix multiplication is a contraction over one shared dimension.
Mathematical notation:
For matrices and :
Code example:
// Matrix multiplication: contract one shared dimension
var A = random_tensor([3, 4],as_complex) // 3×4 matrix
var B = random_tensor([4, 5],as_complex) // 4×5 matrix
var C = contract(A, B, [1], [0]) // Contract dimension 1 of A with dimension 0 of B
print(C.shape()) // [3, 5]
Hermitian Inner Product with Conjugation
When working with complex tensors, we often need the conjugate contraction for Hermitian inner products. This specialized contraction kernel optimizes the conjugation by fusing the operation with the contraction, lowering both memory and time consumption.
Mathematical notation:
For tensors :
Code example:
// Hermitian inner product: contract all dimensions with conjugation
var A = random_tensor([3, 4],as_complex)
var B = random_tensor([3, 4],as_complex)
var inner_product = contract_conjugate(A, B, [0, 1], [0, 1])
// Result is a 0-dimensional tensor ( a scalar)
// Computes: Σᵢⱼ conj(A[i,j]) * B[i,j]
print(inner_product) // Complex order 0 tensor
Higher-Dimensional Tensor Contraction
Contractions generalize naturally to higher dimensions, which is essential for tensor networks.
Mathematical notation:
For a 3-tensor and a 2-tensor :
Code example:
// Contract a 3D tensor with a matrix
var T = random_tensor([2, 3, 4],as_complex) // 3D tensor
var M = random_tensor([3, 5],as_complex) // 2D matrix
var result = contract(T, M, [1], [0]) // Contract dimension 1 of T with dimension 0 of M
print(result.shape()) // [2, 4, 5]
// Computes: result[i,k,l] = Σⱼ T[i,j,k] * M[j,l]
Partial Conjugate Contraction
This operation computes a matrix product where the left-hand tensor is conjugated, but not transposed.
Mathematical notation:
For tensors and :
Code example:
// Partial conjugate contraction (adjoint-like operation)
var A = random_tensor([2, 3],as_complex) // 2×3 tensor
var B = random_tensor([3, 5],as_complex) // 3×5 tensor
var result = contract_conjugate(A, B, [1], [0])
print(result.shape()) // [2, 5]
// Computes: C[i,k] = Σⱼ conj(A[i,j]) * B[j,k]
Multiple Dimension Contraction
You can contract multiple dimensions simultaneously (useful in tensor network algorithms).
Mathematical notation:
For 4-tensors and :
Code example:
// Contract multiple dimensions at once
var A = random_tensor([2, 3, 4, 5],as_complex) // 4D tensor
var B = random_tensor([3, 4, 6, 7],as_complex) // 4D tensor
var result = contract(A, B, [1, 2], [0, 1]) // Contract dimensions [1,2] of A with [0,1] of B
print(result.shape()) // [2, 5, 6, 7]
// Computes: result[i,m,l,n] = Σⱼₖ A[i,j,k,m] * B[j,k,l,n]
Key Properties
- Associativity: Contractions can be performed in different orders (though computational efficiency and numerical accuracy may vary drastically)
- Dimension Matching: Contracted dimensions must have the same size
- Index Ordering: The order of uncontracted dimensions is preserved from left (first tensor) to right (second tensor)
- Generality: Many linear algebra operations (dot product, matrix multiply, trace, etc.) are special cases of contraction
See Also
- Tensor: Introduction to tensors and their properties
- Factorization: Tensor decomposition methods