Skip to content

For AI agents

A dense, rule-oriented map of liulu for coding agents. Read this first, then the specific page you need. The canonical spec is plan.md in the repo root; the project working agreement is CLAUDE.md.

What this package is

A streaming-model RSD predictor: given real-space \(\xi(r)\) + pairwise velocity moments + a velocity PDF, it returns redshift-space \(\xi^s(s_\perp,s_\parallel)\) and multipoles \(\xi_0,\xi_2,\xi_4\). Entry point: from liulu import StreamingModel.

Hard architecture rules (do not violate)

  1. liulu/physics/ = astrophysical content only. No np.trapz, scipy.integrate, FFTs, or grid construction. New physics = new class inheriting an ABC in physics/base.py.
  2. liulu/numerics/ = pure numerics. No cosmological parameters, no knowledge of what \(\xi\) or \(\mathcal{P}\) mean. Signatures are f, a, b, tol style — never a Cosmology or moments object.
  3. liulu/model.py is the only wiring point, via constructor injection.

Conventions (load-bearing)

  • Units: Mpc/\(h\), km/s, \(aH\) in km/s/(Mpc/\(h\)). Convert only at I/O.
  • Moments: m_ij (about origin) / c_ij (central); i=radial, j=tangential order. Odd tangential orders are auto-zero. Dispatcher: moments.get_moment(r, r_order, t_order, mode). Do not add parallel sigma_*/gamma_*/kappa_* accessors — those are inputs to TabulatedMoments, converted to c_ij.
  • Geometry: integrate over y (real-space LOS sep); r=sqrt(s_perp^2+y^2), v_los=aH*(s_par-y)*sign(y). PDF signature pdf(v_los, r_perp, r_par) with r_par >= 0 — pass |y|.
  • LOS projection (physics/los_projection.py) is geometry, not a model — not an ABC. Extend by adding higher c_ij methods, never by hand-unrolling.

Gotchas that have bitten before

  • n_y >= 300 in StreamingModel. Below that the Fingers-of-God dip in \(\xi_2\) (\(s\sim3\)\(5\)) is under-resolved and any fit/objective on it is biased.
  • TabulatedXi defaults to log–log interpolation (near-exact for power-law \(\xi\)); log-linear overestimates the convex curve and biased the monopole ~1.4% high. Falls back to log-linear where \(\xi\le0\).
  • Moments edge-extrapolate below \(r_\min\) so dispersions plateau; a zero variance would collapse the PDF to a delta and silently drop pairs.
  • Skew-t caches its \((\gamma_1,\gamma_2)\to(\alpha,\nu)\) table at liulu/data/skewt_param_table.npz; bump _SKEWT_TABLE_VERSION on format change. NIG needs no table (closed-form inversion).
  • When measuring moments with the external PairVel.jl, set JULIA_NUM_THREADS=1 — multithreaded PyJulia segfaults via a PyCall finalizer race.

Velocity PDF — settled recommendation

Use NIGPDF (analytic, zero-tuning, best four-moment shape). Then a single tuned constant-\(\lambda\) GHD; then a measured-PDF emulator. A scale-dependent \(\lambda(r)\) is not worth it — it overfits (wins in-sample, fails to generalise across bias and gravity). Evidence: Validation.

Where things live

need file
driver / integral / multipoles liulu/model.py
ABCs liulu/physics/base.py
xi(r) providers liulu/physics/real_space.py
pairwise moments liulu/physics/pairwise_velocity.py
velocity PDFs liulu/physics/velocity_pdf.py
LOS projection liulu/physics/los_projection.py
interpolation liulu/numerics/interpolation.py
Hankel transforms liulu/numerics/hankel.py
tests liulu/tests/
spec plan.md

Environment / commands

micromamba run -n cosemu python -m pytest liulu/tests/ -v   # tests
micromamba run -n cosemu mkdocs build                       # this site

Always prefix Python/pip with micromamba run -n cosemu.