Skip to article frontmatterSkip to article content
Site not loading correctly?

This may be due to an incorrect BASE_URL configuration. See the MyST Documentation for reference.

Matrix-Free GP with ImplicitKernelOperator

For large NN, forming the N×NN \times N kernel matrix KK requires O(N2)O(N^2) memory and O(N3)O(N^3) time for dense factorizations. ImplicitKernelOperator avoids materializing KK entirely: it computes KvK v on-the-fly by evaluating the kernel function row-by-row, using only O(N)O(N) memory. Combined with CG-based solvers, this enables GP inference on problems that are too large for dense methods.

What you’ll learn:

  1. Building a matrix-free kernel operator with ImplicitKernelOperator
  2. Solving kernel systems with CGSolver, PreconditionedCGSolver, and BBMMSolver
  3. Using structural tags for metadata
  4. Exploiting orthonormal low-rank structure with LowRankUpdate
  5. Full GP prediction: implicit vs dense

1. Setup

<function __main__.<lambda>(op)>

We generate a 1D GP regression problem with N=2000N = 2000 noisy observations of a smooth function.

Training set: N = 2000, D = 1
Noise variance: 0.1

2. Build ImplicitKernelOperator

We define a scalar RBF kernel

k(x,x′)=σf2exp⁡ ⁣(−∥x−x′∥22ℓ2)k(x, x') = \sigma_f^2 \exp\!\left(-\frac{\|x - x'\|^2}{2 \ell^2}\right)

where x,x′x, x' are 1D arrays of shape (D,). The kernel function is passed to ImplicitKernelOperator, which wraps it into a lineax operator that computes (K+σn2I)v(K + \sigma_n^2 I) v without ever forming KK.

Operator size: 2000 x 2000

The operator supports mv (matrix-vector product) for CG-based methods. It also has as_matrix() for debugging, but that materializes the full N×NN \times N matrix -- exactly what we want to avoid at scale.

Matvec error (implicit vs dense): 5.68e-14

3. Solve with CGSolver

CGSolver uses lineax CG for the linear solve (K+σn2I)α=y(K + \sigma_n^2 I) \alpha = y and matfree’s stochastic Lanczos quadrature (SLQ) for the log-determinant. It only needs matvec access -- no matrix materialization.

CG solve residual: 9.80e-07
CG stochastic logdet: -4522.7308
Dense logdet:         -4522.1695
Logdet error:         5.61e-01

4. Solve with PreconditionedCGSolver

PreconditionedCGSolver builds a rank-kk partial Cholesky preconditioner that dramatically reduces the number of CG iterations for ill-conditioned kernel systems. The shift parameter should match the noise variance.

Preconditioned CG solve residual: 9.76e-08
Max |alpha_pcg - alpha_cg|:       2.02e-06

5. Solve with BBMMSolver

BBMMSolver (Gardner et al. 2018) jointly computes the solve and log-determinant via solve_and_logdet, amortizing the matvec cost.

BBMM solve residual: 9.80e-07
BBMM logdet:         -4527.8656
Dense logdet:        -4522.1695

Solver comparison

All three iterative solvers converge to the same solution.

Max difference between solvers:
  CG   vs PCG:  2.02e-06
  CG   vs BBMM: 0.00e+00
  PCG  vs BBMM: 2.02e-06

6. Tags for structural metadata

ImplicitKernelOperator accepts lineax tags to declare structural properties. Kernel matrices from stationary kernels are symmetric and positive semi-definite; declaring this lets lineax and gaussx exploit the structure.

is_symmetric:              True
is_positive_semidefinite:  True

7. Orthonormal low-rank updates via LowRankUpdate

When a truncated SVD approximation of the kernel matrix is available (e.g., from a Nystrom approximation), LowRankUpdate can represent the operator as L+Udiag⁡(S)V⊤L + U \operatorname{diag}(S) V^\top. Setting orthonormal=True preserves the SVD-specific symmetry inference without a separate operator class.

Here we compute a dense truncated SVD for demonstration. In practice, you would obtain U,S,VU, S, V from a randomized or Nystrom method without forming the full matrix.

LowRankUpdate: rank-50 approximation
Operator size: 2000 x 2000
SVD solve residual: 1.05e-06
SVD logdet:   -4528.3541
Dense logdet: -4522.1695

8. GP prediction

With α=(K+σn2I)−1y\alpha = (K + \sigma_n^2 I)^{-1} y in hand, the posterior mean at test points X∗X_* is

μ∗=K∗f α\mu_* = K_{*f} \, \alpha

We compare predictions from the implicit (CG) solve with the dense Cholesky baseline.

Max prediction error (CG vs dense): 8.86e-07

9. Plot: implicit vs dense GP predictions

<Figure size 1200x400 with 2 Axes>

Summary

  • ImplicitKernelOperator -- Matrix-free (K+σ2I)v(K + \sigma^2 I) v via on-the-fly kernel evaluation. O(N)O(N) memory.
  • CGSolver -- Iterative CG solve + SLQ logdet. Only needs matvec access.
  • PreconditionedCGSolver -- Partial Cholesky preconditioner for faster CG convergence.
  • BBMMSolver -- Joint solve + logdet via batched CG (Gardner et al. 2018).
  • LowRankUpdate(..., orthonormal=True) -- SVD-parameterized low-rank structure for cheap solves and logdets.

When to use what:

  • Small NN (<5000< 5000): Dense Cholesky is fastest and exact.
  • Medium NN (5000--50000): CGSolver or PreconditionedCGSolver with ImplicitKernelOperator.
  • Large NN (>50000> 50000): BBMMSolver with ImplicitKernelOperator amortizes matvec costs across solve and logdet. Use PreconditionedCGSolver if the system is ill-conditioned.
  • Low-rank structure available: LowRankUpdate(..., orthonormal=True) exploits the factored form directly.