Make PCA projection reproducible given seed - #46
Open
NetZissou wants to merge 2 commits into
Open
Conversation
sklearn auto-selects the randomized SVD solver for large inputs, calling PCA(n_components=2) without `random_state` produced a different projection on every run. Now fixed by passing the seed to the API call. cuML PCA is left unchanged: it has no random_state parameter (passing one raises TypeError and silently falls back to sklearn), and its full-SVD solver is already deterministic. Verified on a V100: cuML PCA stays on GPU path and is reproducible run-to-run.
Verified empirically on both backends (sklearnex-patched and vanilla sklearn on CPU; cuML 26.4 on an H100): with a fixed seed and a pinned backend, PCA/UMAP/KMeans/t-SNE reproduce bit-identically across process restarts, except cuML t-SNE, which RAPIDS documents as not completely deterministic even with random_state (NVIDIA/cuml#2980). Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Collaborator
Author
|
@egrace479 this should be ready for review. |
There was a problem hiding this comment.
Pull request overview
Makes sklearn PCA projections reproducible when a fixed seed is enabled.
Changes:
- Passes the seed to sklearn PCA.
- Documents projection and clustering reproducibility across backends.
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.
| File | Description |
|---|---|
shared/utils/clustering.py |
Seeds sklearn PCA and clarifies cuML behavior. |
README.md |
Adds reproducibility guidance. |
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
|
|
||
| - **PCA** is a deterministic decomposition, with no stochastic optimization involved. cuML PCA uses a full eigendecomposition and always returns the same result, seed or no seed. sklearn can auto-select a randomized SVD solver, so the app passes the seed to make it reproducible. | ||
| - **UMAP** and **KMeans** reproduce exactly on both backends when a seed is set. (Seeded UMAP trades some speed for determinism.) | ||
| - **t-SNE** reproduces on `sklearn` when a seed is set. cuML's implementation is highly parallelized and documented as [not completely deterministic between runs, even with the same `random_state`](https://docs.rapids.ai/api/cuml/stable/api/generated/cuml.manifold.tsne/) (see [rapidsai/cuml#2980](https://github.com/rapidsai/cuml/issues/2980)). Select `sklearn` when t-SNE results need to be reproducible. |
Collaborator
Author
There was a problem hiding this comment.
@egrace479 very interesting comment it made here.
Member
There was a problem hiding this comment.
It seems to have corrected the 26.4 statement to the actual release of 26.04 but then fallen back to semver to say well this clearly should be fine since 26.4 would come after 26.08 😵💫
| reducer = PCA(n_components=2) | ||
| # Pass random_state so the randomized SVD solver (auto-selected for | ||
| # large inputs) is reproducible when a seed is set; None keeps it random. | ||
| reducer = PCA(n_components=2, random_state=seed) |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
sklearn auto-selects the randomized SVD solver for large inputs, calling PCA(n_components=2) without
random_stateproduced a different projection on every run. Now fixed by passing the seed to the API call.cuML PCA is left unchanged: it has no
random_stateparameter (passing one raises TypeError and silently falls back to sklearn), and its full-SVD solver is already deterministic. Verified on a V100: cuML PCA stays on GPU path and is reproducible run-to-run. Changing the solver to "jacobi" doesn't make sense for the interactive scale data with 768 dim.