You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
* Attribute degenerate-fit refusal to AMICA wrapper
Row 5 of the differences table credited the raw PyTorch backend with
refusing transform/get_*/save on a degenerate fit; that guard is the
AMICA wrapper's _check_usable contract. The raw AMICATorchNG backend
has no such guard of its own (tracked as issue #306).
* Document unmapped Fortran keywords
Add a section resolving the page's exhaustiveness contract: points to
fortran_params.py's FORTRAN_UNSUPPORTED_KEYS as the enumeration, names
filter_length/dft_length/decwindow as dead in the reference itself
(alongside the already-documented do_choose_pdfs/Spinv2 dead code),
and records the do_rho-vs-pdftype divergence: Fortran can freeze the
GG shape while keeping pdftype=0, but every pamica backend derives
the freeze from pdftype directly, making that combination unreachable.
Links issues #312/#314 for the live lifecycle/diagnostics gaps.
* Port variance_order to AMICAMLXNG
Adds the EEGLAB back-projected-variance component order (issue #92)
to the MLX backend, mirroring AMICATorchNG.variance_order with MLX's
model-major W layout ((n_models, n, n)) and the unfitted RuntimeError.
Closes the one accessor gap the epic's feature-parity audit found in
an otherwise-complete Phase 3; updates the module docstring's
ported-features claim to match.
Adds cross-backend parity coverage against a float64 AMICATorchNG
twin holding identical fitted parameters (order matches exactly on a
30-iteration multi-model fit with non-degenerate variance gaps, with
a gap-size assertion documenting the tie risk), plus MLX-only
unfitted/invalid-model_idx/permutation tests.
* Correct validation harness backend coverage claim
AGENTS.md claimed the harness runs "both implementations (NG +
NumPy)"; validate_implementations.py only exercises torch vs Fortran.
NumPy parity lives in pytest (test_sample_data_numpy_vs_fortran); MLX
validation lives in mlx_tests/ plus the cross-backend suites.
Extending the harness itself is tracked as issue #315.
* Fix unsupported-key comment for writestep/do_history
The FORTRAN_UNSUPPORTED_KEYS entries for writestep/do_history/
histstep said these have no pamica equivalent; false for the legacy
NumPy backend, which implements all three (numpy_impl/core.py's fit
loop and _write_history). Keeps the keys unsupported here (this
module targets the torch wrapper, which has no matching mechanism)
but corrects the reason: NumPy-only, torch/MLX gap tracked as #312.
* Refresh stale feature-parity status notes
feature_parity.md and progress_summary.md still claimed the runtime-
vs-Fortran benchmark was unmeasured and issue #15 (save/load and
plot_components test coverage) was open; both landed since. Also
corrects progress_summary.md's validation-harness claim (same fix as
AGENTS.md: torch-vs-Fortran only, not NG + NumPy). Adds a header note
to feature_parity.md pointing to amica-differences.md's table as the
live, maintained backend-parity source of truth.
* Align NumPy backend's inert pdftype default to 0
self.pdftype is never read after assignment (this backend always
runs the GG update; _compute_log_pdf takes no pdftype param), so the
old default of 1 was a harmless but confusing mismatch against
torch/MLX's constructor default of 0. Aligned for surface consistency
only; no behavior change.
* Add changelog entry for epic polish round
Summarizes the audit-driven fixes ahead of merge to dev: MLX
variance_order, the doc corrections, and the new tracking issues
(#312, #314, #315) plus the #306 extension.
* Scope variance_order precision claim to defaults
| GPU support | no | yes | CUDA / MPS / CPU automatic (float64 parity runs on CPU/CUDA) |
74
-
| Runtime vs Fortran | baseline |**unmeasured**|the 2-3x criterion has never been benchmarked|
82
+
| Runtime vs Fortran | baseline |**measured, met/exceeded**|CUDA float64 ~4.5x over 16-thread CPU, MLX ~7x on Apple Silicon (#77/#84); see `AGENTS.md` Performance section|
75
83
76
84
## Validation status (issue #24)
77
85
@@ -88,9 +96,10 @@ indistinguishable from Fortran's run-to-run distribution (#27, `.context/issue-2
88
96
89
97
## Remaining roadmap
90
98
91
-
-[]**Performance benchmark** vs the Fortran binary (CPU/CUDA/MPS); verify or revise the 2-3x
92
-
runtime criterion.
99
+
-[x]**Performance benchmark** vs the Fortran binary (CPU/CUDA/MPS); 2-3x runtime criterion
100
+
met/exceeded (#77/#84).
93
101
-[x]**Component sharing** (`share_comps`, `share_start`/`share_iter`, `comp_thresh`) ported to
94
102
`AMICATorchNG` (#60), off by default, behavior-validated on real data.
Copy file name to clipboardExpand all lines: docs/guides/amica-differences.md
+55-1Lines changed: 55 additions & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -16,7 +16,7 @@ that is not listed, that is a bug worth
16
16
| 2 | Zero numerical rank |`numeigs = 0`, continues |`ValueError` naming cause and fix | fitting a zero-dimensional model is not a recoverable state | — (no reason to want it) |
17
17
| 3 | Returned iterate | last EM iterate | highest-likelihood iterate (`keep_best`) | the lrate schedule is non-monotone; late Newton overshoots cut LL variance 12.7x → 2.0x |`keep_best=False`|
18
18
| 4 | Newton | on (`do_newton=1`) | off | isolates the algorithm from initialization for parity work |`do_newton=True`|
19
-
| 5 | Degenerate fits | returns NaN sources, and writes them out on its `writestep` cadence |PyTorch refuses `transform`/`get_*`/`save`; NumPy reports `converged=False` with a `stop_reason`, refuses the final write, and skips each periodic checkpoint with a logged reason (leaving the last valid one on disk) | NaN sources silently poison downstream analysis, and `loadmodout` reads a NaN checkpoint back without complaint | — (see issues #50 and #240) |
19
+
| 5 | Degenerate fits | returns NaN sources, and writes them out on its `writestep` cadence |the `AMICA` wrapper refuses `transform`/`get_*`/`save` (the raw `AMICATorchNG` backend has no such guard of its own — tracked as issue #306); NumPy reports `converged=False` with a `stop_reason`, refuses the final write, and skips each periodic checkpoint with a logged reason (leaving the last valid one on disk) | NaN sources silently poison downstream analysis, and `loadmodout` reads a NaN checkpoint back without complaint | — (see issues #50 and #240) |
20
20
| 6 | Precision | float64 | float64 (float32 on Apple GPUs) | Apple GPUs have no float64; float32 agrees to ~7 significant digits, not bit-parity |`dtype=torch.float64`|
21
21
| 7 | Sensor-space maps |`Spinv` applied internally |`get_sensor_mixing_matrix()`|`get_mixing_matrix()` returns sphered-space `A`; switching its meaning by data conditioning would be worse | — |
22
22
| 8 | Columns merged away by `share_comps`| updated to NaN, then hidden by the `comp_used` mask | frozen at their last finite value (never divided) | a fit must not end holding NaN parameters, mask or no mask; the columns are dead either way | — (see issues #60, #240) |
@@ -589,3 +589,57 @@ Practical notes:
589
589
can appear on disk mid-fit. The final write replaces it — what is on disk when
590
590
`fit` returns is the winner's state, which is a tested claim, not just a
591
591
documented intention.
592
+
593
+
## Unmapped Fortran keywords
594
+
595
+
This page's own contract ("anything not on this page is intended to match the
596
+
reference") only covers *behavior*. A Fortran keyword that pamica's parameter
597
+
translator does not map at all is a separate, narrower question, and it has
598
+
its own enumeration: `pamica/fortran_params.py`'s `FORTRAN_UNSUPPORTED_KEYS`
599
+
lists every keyword the reference parser accepts that this project does not
600
+
translate into a pamica constructor/`fit()` argument, with a one-line reason
601
+
for each. That dict, not this page, is the exhaustive list.
602
+
603
+
Most of those keywords are unmapped because the feature genuinely has no
604
+
pamica equivalent (checkpoint warm-start, per-family EM freeze toggles,
605
+
console/file-reporting cadence, ...). Three, though, are dead even in the
606
+
reference binary itself — the same category as the `do_choose_pdfs` and
607
+
`Spinv2` dead code documented above:
608
+
609
+
-**`filter_length`, `dft_length`** — parsed, printed, and broadcast to every
0 commit comments