potential: pin SCF/Multipole construction-time setup to numpy#986
Conversation
Constructing SCF / Multipole / DiskSCF / DiskMultipole / KuijkenDubinski
potentials ran their pure-numpy coefficient/density-grid quadrature and the
density-lambda arity autodetect while the forced backend default was torch/jax,
so get_namespace(<plain numpy/Python scalar>) returned the backend and torch
rejected the mixed ops (`numpy.ndarray * Tensor` in the SCF integrands; a
swallowed TypeError mis-detecting numOfParam -> wrong-arity Multipole density
lambda). Wrap the construction-time numerical setup in
`with use("numpy", force=True):` (scf_compute_coeffs[_axi/_spherical] +
SCFPotential.from_density arity probe; MultipoleExpansionPotential.from_density
rho_lm quadrature/spline build). This is non-differentiable host setup that
builds the stored numpy coefficient tables; evaluation stays backend-aware.
numpy byte-identical (the forced-numpy default is a no-op on the numpy path):
16 stored coefficient arrays (._Acos/._Asin, ._me._Acos/_Asin, multipole spline
tables) bit-identical parent vs branch; test_scf/test_MultipoleExpansionPotential
/test_amp_mult_divide counts unchanged. Under torch these families now construct
successfully and 12 test_amp_mult_divide entries flip to pass; the 3 remaining
(expwhole*/nonaxiDiskSCF) fail for the separate Potential.normalize-stores-Tensor
central-coercion reason, handled by another PR.
Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## feat/backends #986 +/- ##
==============================================
Coverage 99.93% 99.93%
==============================================
Files 253 253
Lines 39803 39810 +7
Branches 839 845 +6
==============================================
+ Hits 39778 39785 +7
Misses 25 25 ☔ View full report in Codecov by Harness. 🚀 New features to boost your workflow:
|
All-backend test status (jax / torch)Commit Green is achieved via the checked-in xfail-ledger ( Overall: jax: 1050 passed · 272 xfail · 725 deferred | torch: 782 passed · 1261 xfail · 1 deferred Ledger size: 2357 entries (jax=284, torch=2073).
Per-shard counts
|
What
Burndown PR-4 (
SCFPotential.py+MultipoleExpansionPotential.py). Constructing SCF/Multipole/DiskSCF/DiskMultipole/KuijkenDubinski potentials ran their pure-numpy coefficient/density-grid quadrature + density-lambda arity autodetect while the forced backend default was torch/jax, soget_namespace(<plain scalar>)returned the backend and torch rejected the mixed ops (numpy.ndarray * Tensor; a swallowedTypeErrormis-detecting a Multipole density lambda's arity). Wrap the construction-time numerical setup inwith use("numpy", force=True):. This is non-differentiable host setup that builds the stored numpy coefficient tables; evaluation stays backend-aware (the jax/torch eval tables are built lazily, outside the wrap).Byte-identity + review
numpy byte-identical (forced-numpy is a no-op on the numpy default): 118 stored coefficient/table attributes bit-identical parent vs branch;
test_scf/test_MultipoleExpansionPotential/test_amp_mult_dividecounts unchanged. Under torch these families now construct and 12test_amp_mult_divideentries flip to pass; the 3 remaining (expwhole*/nonaxiDiskSCF) fail for the separatePotential.normalize-stores-Tensor central-coercion reason (PR-3b). Adversarially reviewed (byte-identity, eval-path-not-pinned, context-manager exception/nesting safety, no missed/double-wrapped paths — all refuted).🤖 Generated with Claude Code