Skip to content

HMF — hmf

Cumulative halo mass function n(>M): the comoving number density of haloes above each mass threshold.

Default changed 2026-09-03 — the routed extrapolation emulator

reg.predict("hmf", ...) now serves the hmf_extrap across-design emulator by default (both gravities, z = 0.25 and z = 0.00): an anchored-ratio extrapolation product reaching log₁₀M = 16, evaluated on the unchanged legacy grid. The pre-promotion (Phase-1) emulator is embedded bit-for-bit and stays available with route="legacy". reg.predict_mass("hmf", ...) newly serves arbitrary masses over log₁₀M ∈ [11, 16]. Full record: doc/hmf_extrapolation_spec.md §6b.

n   = reg.predict("hmf", "LCDM", 0.25, [0.31, 0.677, 0.967, 0.83])  # (1, 23)
old = reg.predict("hmf", "LCDM", 0.25, th, route="legacy")          # Phase-1
nm  = reg.predict_mass("hmf", "LCDM", 0.25, th, [14.9, 15.5])       # [11, 16]
art = reg.load("hmf", "LCDM", 0.25)
art.coord                                          # log10M left edges (legacy grid)
  • Output: (1, 23) at z = 0.25 ((1, 25) at z = 0), units (Mpc/h)⁻³ — identical grid on both routes.
  • Default route (extrap): log-PCA (k = 4) + per-component GP over the per-node posterior n(>M) product curves (Tinker08-anchored GP ratio, box-corrected σ tables); f(R) composes the ΛCDM leg with an emulated seed-paired boost. Trained on design imodels 1–64 + 69–72 (65–68 excluded); fixed-redshift throughout.
  • Legacy route: weighted-PCA + per-component GP on n(>M), n_components = 4, trained span [12.5, 14.7].

Retraining caveat

haloemu train hmf would replace the router with a Phase-1-style artifact. Re-promote afterwards with haloemu/campaigns/hmf_extrap_promote.py --stage promote.

Accuracy (z = 0.25)

Default route, against the held-out 100-box fiducials (never in training):

  • ΛCDM n(>M): 0.01 / 0.3 / 0.9 / 6.4 % at log₁₀M = 13 / 14 / 14.5 / 15; design leave-one-node-out at 14.5: 1.0 % RMS.
  • f(R) (boost composition vs F5n1): 0.05 / 0.2 / 2.0 / 3.5 % at the same marks; design LOO at 14.5: 2.8 % RMS.

Legacy route (unchanged quotes): ΛCDM interior leave-one-out 0.49 % RMS (median at the SEM floor); F5n1 fiducial 0.49 % RMS, F6n1 median 0.15 %, tail max 0.67 % to log₁₀M ≈ 14.7.

Redshift

Registered at z = 0.25 and z = 0.00 for both gravities; both are the routed default. Everything is fixed-redshift — no interpolation in z.

f(R)

On both routes the f(R) hmf is a multiplicative seed-paired boost composed with the ΛCDM leg (legacy: MGBoostEmulator on the checksum-fixed Phase-1 base; extrap: the emulated product boost). The legacy screened-tail accuracy depended critically on optimizer convergence:

The screened-tail story (legacy route)

The boost used to ring below the measured n(>M) at the chameleon screening transition (log₁₀M > 14 at F6n1: down to −24 %, χ ≈ 95), long blamed on design sampling. It was actually optimizer under-convergence at n_restarts = 3. Raising to n_restarts = 10 fixed it (F6n1 median 0.15 %, tail max 0.67 %) with zero new simulations. Only the hmf boost was restart-sensitive — its ratio carries the sharp screened-tail structure.

A linear mean for the boost was tested and rejected (it trades F5n1 for F6n1); restarts is the real fix.

Evidence scripts

Default route: campaigns/hmf_extrap_promote.py --stage verify, campaigns/hmf_extrap_emu.py --stage loo, campaigns/hmf_extrap_compare_old.py (old-vs-new figures); campaign record under degrace_pilot/hmf/. Legacy route: hmf_validation.py, improve_hmf_gate.py, restarts_sweep.py, fRn1_fiducial_oos.py --imodel {0,-1}.