Commit 32d6aa5
perf: use covariance path in svd_whiten when n_samples >= n_features
For tall data matrices (n >> p), the previous implementation called
np.linalg.svd(X, full_matrices=False), allocating an n×p matrix U and
computing O(n·p²) FLOPs via LAPACK dgesdd.
When n >= p it is equivalent and more efficient to:
1. Form the p×p sample covariance C = Xᵀ X / (n-1) [O(n·p²) FLOPs, O(p²) memory]
2. Diagonalise C with eigh [O(p³) FLOPs]
3. Compute the whitened data X @ W [O(n·p²) FLOPs, no large intermediate]
This avoids allocating the n×p U matrix as an intermediate (169 MB for
n=54k, p=392) and lets BLAS DSYRK/DGEMM handle the heavy lifting, which
is typically 2–3× faster than LAPACK dgesdd for tall matrices.
The original SVD path is retained for the n < p (wide matrix) case.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>1 parent 87e0203 commit 32d6aa5
1 file changed
Lines changed: 29 additions & 16 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
10 | 10 | | |
11 | 11 | | |
12 | 12 | | |
13 | | - | |
| 13 | + | |
14 | 14 | | |
15 | | - | |
| 15 | + | |
16 | 16 | | |
17 | 17 | | |
| 18 | + | |
| 19 | + | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
| 23 | + | |
| 24 | + | |
| 25 | + | |
18 | 26 | | |
19 | 27 | | |
20 | 28 | | |
| |||
24 | 32 | | |
25 | 33 | | |
26 | 34 | | |
27 | | - | |
28 | | - | |
29 | | - | |
30 | | - | |
31 | | - | |
32 | | - | |
33 | | - | |
34 | | - | |
35 | | - | |
36 | | - | |
37 | | - | |
38 | | - | |
39 | | - | |
40 | | - | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
| 39 | + | |
| 40 | + | |
| 41 | + | |
| 42 | + | |
| 43 | + | |
| 44 | + | |
| 45 | + | |
| 46 | + | |
| 47 | + | |
| 48 | + | |
| 49 | + | |
| 50 | + | |
| 51 | + | |
| 52 | + | |
| 53 | + | |
41 | 54 | | |
42 | 55 | | |
43 | 56 | | |
| |||
0 commit comments