Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Again more docstrings #447

Merged
merged 3 commits into from
Aug 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion firecrown/likelihood/number_counts.py
Original file line number Diff line number Diff line change
Expand Up @@ -231,7 +231,7 @@ def apply(
) -> NumberCountsArgs:
"""Apply a magnification bias systematic.

:param tools: currently unused, by required by the interface
:param tools: currently unused, but required by the interface
:param tracer_arg: a NumberCountsArgs object with values to be updated

:return: an updated NumberCountsArgs object
Expand Down
107 changes: 80 additions & 27 deletions firecrown/likelihood/source.py
Original file line number Diff line number Diff line change
Expand Up @@ -29,19 +29,15 @@ class SourceSystematic(Updatable):
the `apply` method of different subclasses are different.
"""

def read(self, sacc_data: sacc.Sacc):
"""Call to allow this object to read from the appropriate sacc data."""
def read(self, sacc_data: sacc.Sacc) -> None:
"""Call to allow this object to read from the appropriate sacc data.

:param sacc_data: The SACC data object to be read
"""

class Source(Updatable):
"""An abstract source class (e.g., a sample of lenses).

Parameters
----------
systematics : list of str, optional
A list of the source-level systematics to apply to the source. The
default of `None` implies no systematics.
"""
class Source(Updatable):
"""The abstract base class for all sources."""

systematics: Sequence[SourceSystematic]
cosmo_hash: None | int
Expand All @@ -57,22 +53,30 @@ def __init__(self, sacc_tracer: str) -> None:
self.sacc_tracer = sacc_tracer

@final
def read(self, sacc_data: sacc.Sacc):
"""Read the data for this source from the SACC file."""
def read(self, sacc_data: sacc.Sacc) -> None:
"""Read the data for this source from the SACC file.

:param sacc_data: The SACC data object to be read
"""
if hasattr(self, "systematics"):
for systematic in self.systematics:
systematic.read(sacc_data)
self._read(sacc_data)

@abstractmethod
def _read(self, sacc_data: sacc.Sacc):
"""Abstract method to read the data for this source from the SACC file."""
def _read(self, sacc_data: sacc.Sacc) -> None:
"""Abstract method to read the data for this source from the SACC file.

:param sacc_data: The SACC data object to be read
"""

def _update_source(self, params: ParamsMap):
def _update_source(self, params: ParamsMap) -> None:
"""Method to update the source from the given ParamsMap.

Any subclass that needs to do more than update its contained :class:`Updatable`
objects should implement this method.

:param params: the parameters to be used for the update
"""

@final
Expand All @@ -81,25 +85,36 @@ def _update(self, params: ParamsMap):

This clears the current hash and tracer, and calls the abstract method
`_update_source`, which must be implemented in all subclasses.

:param params: the parameters to be used for the update
"""
self.cosmo_hash = None
self.tracers = []
self._update_source(params)

@abstractmethod
def get_scale(self) -> float:
"""Abstract method to return the scales for this `Source`."""
"""Abstract method to return the scale for this `Source`.

:return: the scale
"""

@abstractmethod
def create_tracers(self, tools: ModelingTools):
"""Create tracers for this `Source`, for the given cosmology."""
"""Abstract method to create tracers for this Source.

:param tools: The modeling tools used for creating the tracers
"""

@final
def get_tracers(self, tools: ModelingTools) -> Sequence[Tracer]:
"""Return the tracer for the given cosmology.

This method caches its result, so if called a second time with the same
cosmology, no calculation needs to be done.

:param tools: The modeling tools used for creating the tracers
:return: the list of tracers
"""
ccl_cosmo = tools.get_ccl_cosmology()

Expand Down Expand Up @@ -128,6 +143,10 @@ def determine_field_name(field: None | str, tracer: None | str) -> str:

It is a static method only to keep it grouped with the class for which it is
defining the initialization policy.

:param field: the (stub) name of the field
:param tracer: the name of the tracer
:return: the full name of the field
"""
if field is not None:
return field
Expand All @@ -144,7 +163,7 @@ def __init__(
halo_profile: None | pyccl.halos.HaloProfile = None,
halo_2pt: None | pyccl.halos.Profile2pt = None,
):
"""Initialize a new Tracer based on the pyccl.Tracer which must not be None.
"""Initialize a new Tracer based on the provided tracer.

Note that the :class:`pyccl.Tracer` is not copied; we store a reference to the
original tracer. Be careful not to accidentally share :class:`pyccl.Tracer`s.
Expand All @@ -154,6 +173,13 @@ def __init__(

If no `field` is given, then the attribute :attr:`field` is set to either
(1) the tracer_name, if one was given, or (2) 'delta_matter'.

:param tracer: the pyccl.Tracer used as the basis for this Tracer.
:param tracer_name: optional name of the tracer.
:param field: optional name of the field associated with the tracer.
:param pt_tracer: optional non-linear perturbation theory tracer.
:param halo_profile: optional halo profile.
:param halo_2pt: optional halo profile 2-point object.
"""
assert tracer is not None
self.ccl_tracer = tracer
Expand All @@ -165,12 +191,18 @@ def __init__(

@property
def has_pt(self) -> bool:
"""Return True if we have a pt_tracer, and False if not."""
"""Answer whether we have a perturbation theory tracer.

:return: True if we have a pt_tracer, and False if not.
"""
return self.pt_tracer is not None

@property
def has_hm(self) -> bool:
"""Return True if we have a halo_profile, and False if not."""
"""Answer whether we have a halo profile.

:return: True if we have a halo_profile, and False if not.
"""
return self.halo_profile is not None


Expand All @@ -193,13 +225,19 @@ class SourceGalaxyArgs:


class SourceGalaxySystematic(SourceSystematic, Generic[_SourceGalaxyArgsT]):
"""Abstract base class for all galaxy based source systematics."""
"""Abstract base class for all galaxy-based source systematics."""

@abstractmethod
def apply(
self, tools: ModelingTools, tracer_arg: _SourceGalaxyArgsT
) -> _SourceGalaxyArgsT:
"""Apply method to include systematics in the tracer_arg."""
"""Apply method to include systematics in the tracer_arg.

:param tools: the modeling tools use to update the tracer arg
:param tracer_arg: the original source galaxy tracer arg to which we
apply the systematic.
:return: a new source galaxy tracer arg with the systematic applied
"""


_SourceGalaxySystematicT = TypeVar(
Expand Down Expand Up @@ -236,8 +274,16 @@ def __init__(self, sacc_tracer: str) -> None:
default_value=SOURCE_GALAXY_SYSTEMATIC_DEFAULT_DELTA_Z
)

def apply(self, tools: ModelingTools, tracer_arg: _SourceGalaxyArgsT):
"""Apply a shift to the photo-z distribution of a source."""
def apply(
self, tools: ModelingTools, tracer_arg: _SourceGalaxyArgsT
) -> _SourceGalaxyArgsT:
"""Apply a shift to the photo-z distribution of a source.

:param tools: the modeling tools use to update the tracer arg
:param tracer_arg: the original source galaxy tracer arg to which we
apply the systematic.
:return: a new source galaxy tracer arg with the systematic applied
"""
dndz_interp = Akima1DInterpolator(tracer_arg.z, tracer_arg.dndz)

dndz = dndz_interp(tracer_arg.z - self.delta_z, extrapolate=False)
Expand All @@ -263,15 +309,20 @@ def __init__(self, field: str = "delta_matter"):
"""Specify which 3D field should be used when computing angular power spectra.

:param field: the name of the 3D field that is associated to the tracer.
Default: `"delta_matter"`
"""
super().__init__()
self.field = field

def apply(
self, tools: ModelingTools, tracer_arg: _SourceGalaxyArgsT
) -> _SourceGalaxyArgsT:
"""Apply method to include systematics in the tracer_arg."""
"""Apply method to include systematics in the tracer_arg.

:param tools: the modeling tools used to update the tracer_arg
:param tracer_arg: the original source galaxy tracer arg to which we
apply the systematics.
:return: a new source galaxy tracer arg with the systematic applied
"""
return replace(tracer_arg, field=self.field)


Expand Down Expand Up @@ -299,11 +350,13 @@ def __init__(
)
self.tracer_args: _SourceGalaxyArgsT

def _read(self, sacc_data: sacc.Sacc):
def _read(self, sacc_data: sacc.Sacc) -> None:
"""Read the galaxy redshift distribution model from a sacc file.

All derived classes must call this method in their own `_read` method
after they have read their own data and initialized their tracer_args.

:param sacc_data: The SACC data object to be read
"""
try:
tracer_args = self.tracer_args
Expand Down
Loading
Loading