tests: make test_orbit energy/Jacobi conservation backend-tolerant (numpy.asarray)#982
Conversation
…umpy.asarray) test_energy_jacobi_conservation and test_energy_conservation_linear compute numpy.std(tEs)/numpy.mean(tEs) with tEs = o.E(ttimes) (and tJacobis = o.Jacobi). Under the forced torch backend o.E()/o.Jacobi() return a torch tensor (galpy computes the CORRECT values), and numpy.std(<tensor>) dispatches to torch's Tensor.std which rejects numpy's kwargs -> TypeError; jax materialises so passed. Wrap every o.E(...)/o.Jacobi(...) output that feeds a numpy host op in numpy.asarray(...) (the #952 convention). numpy.asarray on a numpy array is an identity no-op, so the numpy path is byte-identical (192 passed / 0 skipped, identical on parent and branch). Test-only; Orbits.py and the ledger untouched. 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 #982 +/- ##
==============================================
Coverage 99.93% 99.93%
==============================================
Files 253 253
Lines 39803 39803
Branches 840 844 +4
==============================================
Hits 39778 39778
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: 1051 passed · 271 xfail · 725 deferred | torch: 764 passed · 1279 xfail · 1 deferred Ledger size: 2357 entries (jax=284, torch=2073).
Per-shard counts
|
What
Burndown Phase-1 PR (2 of 2 test-only). Makes the energy/Jacobi conservation asserts in
tests/test_orbit.pytolerant of a forced jax/torch backend.Why
test_energy_jacobi_conservationandtest_energy_conservation_linearcomputenumpy.std(tEs)/numpy.mean(tEs)withtEs = o.E(ttimes)(andtJacobis = o.Jacobi). Under forced torch,o.E()/o.Jacobi()return a torch tensor (galpy computes the correct values), andnumpy.std(<tensor>)dispatches to torch'sTensor.std(ddof=,dtype=,out=,axis=)which rejects numpy's kwargs →TypeError. jax passed only because numpy ufuncs auto-materialise it. Test-harness issue, not a galpy bug.Change (test-only)
Wrap every
o.E(...)/o.Jacobi(...)output that feeds a numpy host op — thestd/meanfeeders and the deeperfirstTest(a-b)**2arithmetic asserts — innumpy.asarray(...)(the #952 convention). 73 wraps;Orbits.pyand the ledger are not touched.Byte-identity
numpy.asarray(<numpy array>)is an identity no-op → numpy path byte-identical. Verified: both functions give 192 passed / 0 skipped, identical on parent (feat/backends) and branch (AST of the two functions is identical after stripping the wraps). Adversarially reviewed.Validation (CPU, CI-parity)
energy_jacobi+ ~23/30energy_linearledger nodeids flip to pass (verified the assertions pass numerically, not just dodge the TypeError).Scope note
Nodeids that fail earlier — in galpy setup (
tp.normalizescalar coercion under forced torch), inOrbit.L()(thenumpy.ndarray * Tensorcross-product), or in the leapfrog integrator — are not fixed here and stay correctly ledgered; they're handled by the central-coercion /Orbits.L()/ integrator source PRs. This PR only clears thenumpy.std(tensor)harness failures.🤖 Generated with Claude Code