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

Some changes in the class Simulation and in IO #293

Merged
merged 3 commits into from
Mar 1, 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: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
# HEAD

- **Breaking change**: Reworking of the IO, `write_observations` and `read_observations` are now part of the class simulation [#293](https://github.com/litebird/litebird_sim/pull/293)

- Support for numpy.float128 made optional, this fixes importing issue on ARM architectures [#286](https://github.com/litebird/litebird_sim/pull/286)

- Improve the documentation about noise simulations [#283](https://github.com/litebird/litebird_sim/pull/283)
Expand Down
13 changes: 11 additions & 2 deletions docs/source/mapmaking.rst
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
.. _mapmaking:

Map-making
==========

Expand Down Expand Up @@ -117,7 +119,7 @@ alternatively pointings can be provided as a list of numpy arrays.)
The result is an instance of the class :class:`.BinnerResult`
and contains both the I/Q/U maps and the covariance matrix.

The :func:`.make_binned_map` has a high level interface in the class
The function :func:`.make_binned_map` has a high level interface in the class
:class:`.Simulation` that bins the content of the observations into maps
The syntax is identical to :func:`.make_binned_map`::

Expand Down Expand Up @@ -335,6 +337,14 @@ instance of the class :class:`.DestriperParameters`::
The result is an instance of the class :class:`.DestriperResult`, which
is similar to :class:`.BinnerResult` but it contains much more information.

The function :func:`.make_destriped_map` has a high level interface in the class
:class:`.Simulation` that applies the destriper algorithm to all the
observations in the simulation.
The syntax is identical to :func:`.make_destriped_map`::

result = sim.make_destriped_map(nside=nside)
healpy.mollview(result.destriped_map)

We will now explain how a destriper works and what is the meaning of each
parameter in the classes :class:`.DestriperParameters` and
:class:`.DestriperResult`. Apart from KS2009, another source of information
Expand Down Expand Up @@ -580,7 +590,6 @@ You can save the results of the destriper using the function
using MPI, you should call both functions on *all* the MPI processes,
and the number of processes should be the same between the two calls.


How the N_obs matrix is stored
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

Expand Down
8 changes: 5 additions & 3 deletions docs/source/observations.rst
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
.. _observations:

Observations
============

Expand Down Expand Up @@ -225,12 +227,12 @@ following information are saved and restored:
- Global and local flags saved in ``.global_flags`` and
``.local_flags`` (see below).

The function used to save observations is :func:`.write_observations`,
which works with a :class:`.Simulation` object; if you prefer to
The function used to save observations is :func:`.Simulation.write_observations`,
which acts on a :class:`.Simulation` object; if you prefer to
operate without a :class:`.Simulation` object, you can call
:func:`.write_list_of_observations`.

To read observations, you can use :func:`.read_observations` and
To read observations, you can use :func:`.Simulation.read_observations` and
:func:`.read_list_of_observations`.


Expand Down
32 changes: 32 additions & 0 deletions docs/source/simulations.rst
Original file line number Diff line number Diff line change
Expand Up @@ -487,6 +487,38 @@ contains the size of the TOD array, the names of the detectors,
and other useful information. Refer to the documentation of
each class to know what is inside.

High level interface
--------------------

The class :class:`.Simulation` has a powerfull high level
interface that allows to quickly generate a scanning strategy
allocate the observations, generate simulated timelines
cointaing signal, noise and dipole, build maps, and
save(read) the entire simulation object. The syntax is
straightforward::

sim = lbs.Simulation(...)

sim.set_scanning_strategy(...)
sim.set_instrument(...)
sim.create_observations(...)
sim.compute_pointings()

sim.compute_pos_and_vel()
sim.add_dipole()

sim.fill_tods(...)
sim.add_noise(...)

result = sim.make_destriped_map(nside=nside)
healpy.mollview(result.destriped_map)

sim.write_observations(...)
sim.read_observations(...)

See the documentation in :ref:`observations`, :ref:`scanning-strategy`
:ref:`dipole-anisotropy`, :ref:`timeordered`, :ref:`mapmaking` for
details of the single functions.

API reference
-------------
Expand Down
88 changes: 23 additions & 65 deletions litebird_sim/io.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,11 +12,13 @@
import h5py
import numpy as np

from deprecation import deprecated

from .version import __version__ as litebird_sim_version
from .compress import rle_compress, rle_decompress
from .detectors import DetectorInfo
from .mpi import MPI_ENABLED, MPI_COMM_WORLD
from .observations import Observation, TodDescription
from .simulations import Simulation

__NUMPY_INT_TYPES = [
np.int8,
Expand Down Expand Up @@ -361,59 +363,26 @@ def write_list_of_observations(
return file_list


@deprecated(
deprecated_in="0.11",
current_version=litebird_sim_version,
details="Use Simulation.write_observations",
)
def write_observations(
sim: Simulation,
sim,
subdir_name: Union[None, str] = "tod",
include_in_report: bool = True,
*args,
**kwargs,
) -> List[Path]:
"""Write a set of observations as HDF5

This function is a wrapper to :func:`.write_list_of_observations` that saves
the observations associated with the simulation to a subdirectory within the
output path of the simulation. The subdirectory is named `subdir_name`; if
you want to avoid creating a subdirectory, just pass an empty string or None.

This function only writes HDF5 for the observations that belong to the current
MPI process. If you have distributed the observations over several processes,
you must call this function on each MPI process.

For a full explanation of the available parameters, see the documentation for
:func:`.write_list_of_observations`.
"""

if subdir_name:
tod_path = sim.base_path / subdir_name
# Ensure that the subdirectory exists
tod_path.mkdir(exist_ok=True)
else:
tod_path = sim.base_path

file_list = write_list_of_observations(
obs=sim.observations, path=tod_path, *args, **kwargs
# Here we call the method moved inside Simulation
return sim.write_observations(
subdir_name,
include_in_report,
*args,
**kwargs,
)

if include_in_report:
sim.append_to_report(
"""
## TOD files

{% if file_list %}
The following files containing Time-Ordered Data (TOD) have been written:

{% for file in file_list %}
- {{ file }}
{% endfor %}
{% else %}
No TOD files have been written to disk.
{% endif %}
""",
file_list=file_list,
)

return file_list


def __find_flags(inpf, expected_num_of_dets: int, expected_num_of_samples: int):
flags_matches = [__FLAGS_GROUP_NAME_REGEXP.fullmatch(x) for x in inpf]
Expand Down Expand Up @@ -661,28 +630,17 @@ def read_list_of_observations(
return observations


@deprecated(
deprecated_in="0.11",
current_version=litebird_sim_version,
details="Use Simulation.read_observations",
)
def read_observations(
sim: Simulation,
sim,
path: Union[str, Path] = None,
subdir_name: Union[None, str] = "tod",
*args,
**kwargs,
):
"""Read a list of observations from a set of files in a simulation

This function is a wrapper around the function :func:`.read_list_of_observations`.
It reads all the HDF5 files that are present in the directory whose name is
`subdir_name` and is a child of `path`, and it stores them in the
:class:`.Simulation` object `sim`.

If `path` is not specified, the default is to use the value of ``sim.base_path``;
this is meaningful if you are trying to read back HDF5 files that have been saved
earlier in the same session.
"""
if path is None:
path = sim.base_path

obs = read_list_of_observations(
file_name_list=list((path / subdir_name).glob("**/*.h5")), *args, **kwargs
)
sim.observations = obs
# Here we call the method moved inside Simulation
sim.read_observations(path, subdir_name, *args, **kwargs)
Loading
Loading