Skip to content

Comments

Feature/baryons bhm fedeli#1277

Open
nikosarcevic wants to merge 14 commits intomasterfrom
feature/baryons_bhm_fedeli
Open

Feature/baryons bhm fedeli#1277
nikosarcevic wants to merge 14 commits intomasterfrom
feature/baryons_bhm_fedeli

Conversation

@nikosarcevic
Copy link
Contributor

This PR adds the Fedeli 2014 baryon halo model to CCL and integrates it into the baryons module.

Included are:

  • a full fedeli14 baryon halo–model implementation under
    pyccl/baryons/fedeli14_bhm/, including:

    • numerics/utilities (numerics.py)
    • mass fraction parametrizations (mas_fractions.py)
    • halo profiles (halo_profiles.py)
    • profile interpolation (profile_interpolation.py)
    • halo-model power spectrum calculation (power_spectra.py(
    • These components are wrapped in a central BaryonHaloModel class (baryon_halo_model.py)
  • a public-facing baryons API in
    pyccl/baryons/fedeli14.py, exposing fedeli14 as a multiplicative baryonic
    boost that returns baryon-modified power spectra

  • Advanced users can directly instantiate and customize the
    BaryonHaloModel to experiment with halo ingredients and internal model
    choices.

  • Example notebooks (under fedeli14_bhm/examples/) demonstrating:

    • direct use of BaryonHaloModel
    • comparison with other baryonic prescriptions in CCL.

I also include unit tests covering each fedeli14 component/script.

Note that:

  • implementation follows the existing CCL baryons architecture
  • linting is locally healthy
  • all tests are passing (only testing the added test pytest pyccl/tests/test_baryons_fedeli14*)

this pr is built off of current ccl master

this closes #1276

@coveralls
Copy link

coveralls commented Jan 25, 2026

Pull Request Test Coverage Report for Build 21326062937

Details

  • 813 of 1050 (77.43%) changed or added relevant lines in 8 files are covered.
  • No unchanged relevant lines lost coverage.
  • Overall coverage decreased (-2.7%) to 94.765%

Changes Missing Coverage Covered Lines Changed/Added Lines %
pyccl/baryons/fedeli14_bhm/mass_fractions.py 98 99 98.99%
pyccl/baryons/fedeli14.py 104 107 97.2%
pyccl/baryons/fedeli14_bhm/power_spectra.py 306 315 97.14%
pyccl/baryons/fedeli14_bhm/numerics.py 112 125 89.6%
pyccl/baryons/fedeli14_bhm/baryon_halo_model.py 132 174 75.86%
pyccl/baryons/fedeli14_bhm/halo_profiles.py 48 132 36.36%
pyccl/baryons/fedeli14_bhm/profile_interpolation.py 12 97 12.37%
Totals Coverage Status
Change from base Build 21003793779: -2.7%
Covered Lines: 7385
Relevant Lines: 7793

💛 - Coveralls

@nikosarcevic nikosarcevic force-pushed the feature/baryons_bhm_fedeli branch from a07e69b to 423171e Compare January 25, 2026 03:17
Copy link
Contributor

@carlosggarcia carlosggarcia left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the work, @nikosarcevic. This is great!

This is a massive PR so I think it might be better if we do multiple iterations over a few files. I've started with the API ones. When we settle on those, I will go into the files with the actual implementation.

A few comments:

  • The CI is failing because the coverage level of the code has gone down. You need to write more unit tests to test all new additions to the code; i.e. as many lines as possible, which is what coveralls checks.
  • I think the policy is to put the notebooks in the CCLX repo. So you should move them from this PR.
  • If you come up with a way of making this PR shorter, that will make our lives easier and the lives of those who have to look into this in the future!

The operation applied is:

.. math::
P_{\rm out}(k,a) = P_{\rm in}(k,a)\,B_{\rm fedeli}(k,a).
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Change B -> f, for consistency with the other modules.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

done in c5812c5

(sorry about CI failing, am trying to fix it, i tihnk it is osx-arm64 standard nightmare suddenly)

- If ``renormalize_large_scales=True``, the boost is rescaled (per
scale factor) so that its mean over ``k <= k_renorm_max`` is unity.
- For ``a < a_min`` (currently hard-coded to 0.1 in the application
step), the boost is forced to unity.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this also enforced in Fedeli+2014 or is this an addition?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is an addition in the wrapper

fedeli4 builds the baryonic halo model so that the large-scale limit is physically correct (e.g. the 2halo term recovers linaer theory and the k->0 limits recover the correct mass fractions), but it does not prescribe an explicit renormalization of a boost ratio to unity over a finite low-k range

the `renormalize_large_scales`` option is basically a numerical safeguard to ensure the ratio f(k,a) -> 1 on large scales when dividing by a chosen reference spectrum, given finite grids and interpolation effects.
Elisa and I had this problem on large scales and this is a solution I found.
in a similar fashion, forcing the boost to unity for a < 0.1 is bascially a defensive cutoff to avoid extrapolating the model outside its intended regime and is not also explicitly imposed in fedeli14

"star_x_delta", "star_alpha", "density_mmin", "density_mmax",
}:
val = float(val)
if key in {"n_m"}:
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if -> elif

k: float | FloatArray,
a: float | FloatArray
) -> float | FloatArray:
r"""Evaluate the Fedeli14 boost factor ``B(k,a)``.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same as above B(k,a) -> f(k,a)

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

for i, aval in enumerate(a_use[:, 0]):
out[i, :] = bhm.boost(k=k_1d, a=float(aval), pk_ref=self.pk_ref)

# We need to enforce B(k->0)=1 by renormalizing on large scales.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

B->f

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

per-a."""
b = BaryonsFedeli14(renormalize_large_scales=False)

calls: list[tuple[float, np.ndarray, str]] = []
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

debugging line?

@@ -0,0 +1,312 @@
"""Unit tests for `pyccl.baryons.fedeli14`."""

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Two general comments:

  • I think it's clever the way you use monkeypatch. I'd try to define a single DummyBHM and use the same for all tests. That would shorten the file and make it a bit easier to read, so that I don't have to re-think in each test what this dummy class is doing.
  • Although I guess you will test the output of the actual Fidelly14 boost computation. I think there is value if you add a single test that actually test that you get the right boost, without DummyBHM class.


# sanity: grids unchanged
a0, lk0, _ = pk.get_spline_arrays()
assert np.allclose(a_arr, a0)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it's more explicit to use assert a0 == pytest.approx(a_arr, rel=1e-5). Numpy can change the relative/absolute tolerances and break all our tests.

a0, lk0, _ = pk.get_spline_arrays()
assert np.allclose(a_arr, a0)
assert np.allclose(k_arr, np.exp(lk0))

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All the lines below are a copy of the above?

assert np.allclose(pk_out[1:, :], 20.0) # boosted by 10 for a>=0.1


def test_incl_bary_eff_fixes_absurd_log_flag_data(
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not needed. Remove.

@nikosarcevic
Copy link
Contributor Author

@carlosggarcia thanks for the feedback.
I have appended more tests to increase coverage

also fixed typing in 1638b4e

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Implement Fedeli14 baryon halo model in CCL baryons module

3 participants