skip to content

Why does a closed-form least-squares solve scale cubically in features but linearly in rows?

level: middleimportance: should knowfreq 45%

answer

  1. two stages, two different scalings
  2. rows stream once; features build a matrix
  3. the p-by-p system is the expensive part
  4. roughly n*p^2 plus p^3
  5. memory wall arrives before the time wall

basics

~20 s

Rows are touched once, in a streaming pass building a p-by-p system. Solving that system costs about p^3 and stores p^2 numbers, so total cost is roughly n*p^2 + p^3: wide designs break the exact solve, not tall ones.

solid answer

~40 s

The exact fit has two stages. First you summarise the data into the cross-product matrix `X'X` and the vector `X'y`; that is one streaming pass costing about `n*p^2`, so rows enter linearly and never all need to be in memory. Second you solve the `p x p` system `(X'X) w = X'y`, which costs on the order of `p^3` and stores `p^2` numbers, with `n` appearing nowhere. So a marketing-mix model with 3 million weekly rows and 8 spend channels solves a 9 x 9 system — iterating there would be pointless. A 60,000-column one-hot store-by-SKU design needs a 29 GB cross-product matrix before you factor anything, so you fit iteratively instead. And no real solver inverts anything: it factorises, because forming `X'X` already squares the problem's condition number.

go deeper

for a junior

Recall that fitting a linear model exactly means solving a system whose size is the number of features, not the number of rows. Knowing that many rows with few features is cheap is enough at this level.

for a middle

Explain both stages and their scalings: a streaming pass of about n*p^2 to build the cross-product matrix, then a p^3 solve of a p-by-p system. Be able to plug in numbers for a narrow design and a very wide one.

for a senior

Show you size a fit before you run it: state the p^2 memory footprint, name the crossover you would check, and mention sparsity and conditioning as the real deciders. Knowing that solvers factorise rather than invert marks you out here.

for a principal

Frame this as an architecture choice: a narrow design lets you fit exactly in a single streaming pass with no tuning and no convergence risk, while a wide one commits the team to an iterative pipeline with its own operational surface. Be ready to argue for feature-set width limits on that basis.

## The two costs in an exact least-squares fit The closed-form fit for a linear model with `n` rows and `p` features runs in two stages, and they scale completely differently. **Stage one: summarise the data.** The fit only needs the cross-products of the columns: the `p x p` matrix `X'X` (every feature dotted with every other feature) and the `p`-vector `X'y` (every feature dotted with the target). Building `X'X` means, for each row, adding that row's `p x p` outer product into an accumulator — about `n * p^2` multiply-adds. Rows enter this term **linearly**: doubling the rows doubles this stage and nothing else. It is also a single streaming pass, so the rows never have to be in memory at once. **Stage two: solve the system.** With `X'X` and `X'y` in hand, the weights come from solving the `p x p` linear system `(X'X) w = X'y`. Solving a dense `p x p` system by a factorisation costs on the order of `p^3` operations, and the matrix itself occupies `p^2` numbers. The number of rows does not appear anywhere in this stage. Total: roughly `n*p^2 + p^3`, plus `p^2` memory. That single expression explains every practical decision on this topic. ## Why this makes "big data" the wrong question "Ten million rows" says almost nothing about whether the exact solve is feasible. What matters is the width. **Wide-in-rows, narrow-in-features: solve exactly.** A marketing-mix model with 3 million weekly rows and 8 spend channels fits a 9 x 9 system once the intercept is included. Stage one is 3,000,000 * 81 accumulations — a fraction of a second of arithmetic and one pass over the file. Stage two is a 9 x 9 solve, which is instantaneous. Iterating here would be pointless: you would take many passes over the same 3 million rows to approach, approximately, the answer one pass already gave you exactly. **Wide-in-features: the exact solve falls apart.** A store-by-SKU one-hot design with 60,000 columns has `p^2 = 3.6 * 10^9` entries in `X'X`, which at 8 bytes each is roughly 29 GB before you have solved anything, and `p^3` is on the order of `10^14` operations. The memory wall arrives first: you cannot even hold the system, let alone factor it. This is the situation the exact solve does not survive, and it is the reason to fit iteratively instead — an iterative method never forms `X'X` at all, it only ever needs to multiply by `X` and by `X'`, and it exploits the fact that a one-hot design is mostly zeros. So the switch to an iterative fit is triggered by **`p`**, and secondarily by the sparsity of the design, far more often than by `n`. ## A detail worth getting right: nobody inverts the matrix The textbook formula is written `w = (X'X)^-1 X'y`, and it is common to hear candidates say the method "inverts a matrix". A competent implementation does not. It solves the system by **factorisation** — a Cholesky decomposition of `X'X`, or a QR decomposition of `X` directly — because: - computing an explicit inverse and then multiplying costs more arithmetic than solving once; - forming `X'X` at all **squares the condition number** of the problem, so a design that was merely awkward becomes numerically hopeless. Factorising `X` directly via QR (about `2*n*p^2`) avoids that squaring; - an explicit inverse of a nearly-singular matrix is full of enormous entries that amplify floating-point noise into the answer. The inverse in the formula is notation for "solve this system", not an instruction. ## The intermediate regime Between "9 x 9" and "60,000 columns" there is a wide band where the exact solve is perfectly fine. A few thousand features means a `p^2` matrix of a few tens of millions of entries and a `p^3` solve of a few times `10^10` operations: seconds, on a laptop, however many rows you have — because the rows only cost you the streaming pass. Practitioners routinely underestimate this band and reach for an iterative fit far earlier than they need to, giving up an exact answer for an approximate one. ## What to say when asked to size a fit Give the two terms and then the numbers. State that rows are a one-pass, linear cost that streams; that features drive a `p^2` memory footprint and a `p^3` solve; that the practical failure is usually memory rather than time; and that the answer therefore depends on `p` and on whether the design is dense or sparse. Then name the crossover you would actually check: can I hold a `p x p` matrix of doubles in RAM? If yes, solve exactly. If no, iterate.

  • At what point do you actually give up on the exact solve and fit iteratively?
    The check I run is whether a `p x p` matrix of doubles fits in RAM: at 60,000 columns that is roughly 29 GB, so no. A few thousand features is around a few hundred megabytes and a `p^3` solve of seconds — fine, whatever the row count. Sparsity matters too: a one-hot design is mostly zeros, and an iterative fit exploits that because it only ever multiplies by the design matrix, never forms the dense cross-product.
  • Why do solvers factorise rather than compute the inverse the formula shows?
    Three reasons. Solving once by Cholesky or QR is cheaper than forming an inverse and then multiplying. Forming `X'X` at all squares the condition number, so QR applied to the design matrix directly is numerically safer. And an explicit inverse of a nearly-singular matrix is full of huge entries that amplify floating-point noise straight into the weights. The inverse in `w = (X'X)^-1 X'y` is notation for solve this system.

Walking the aisles to count a warehouse takes one pass however many boxes there are. Building the table of how every box type relates to every other is the part that explodes as the catalogue grows.

saying these in an interview costs you the question

  • Says big data alone rules out the closed-form solve
  • Believes the method literally computes a matrix inverse
  • Thinks doubling the rows multiplies the solve cost cubically
  • Confuses row count with the size of the system being solved
  • Assumes all rows must be held in memory at once

context