odatse.algorithm._algorithm module#

class odatse.algorithm._algorithm.AlgorithmBase(info: Info, runner: Runner | None = None, run_mode: str = 'initial')[source]#

Bases: object

Base class for algorithms, providing common functionality and structure.

Lifecycle#

main() drives the three-phase lifecycle by calling the framework wrappers:

main()
  ├── prepare()   runner.prepare → dispatch(init/resume/continue) → _prepare()
  ├── run()       _run()
  └── post()      _post() → runner.post()

Subclasses implement the hooks with underscore prefix: _prepare() (optional), _run() (required), _post() (required). The plain-named wrappers prepare, run, post are framework internals and must not be overridden in subclasses.

Checkpoint#

Each class declares _checkpoint_attrs (a list of attribute names). __getstate__() walks the MRO and collects them all automatically. Subclasses normally need only declare their own _checkpoint_attrs and override _apply_state() to call super() and restore RNG / algorithm-specific state. Override _save_state() / _load_state() only when extra files (e.g. an external policy object) must be written.

Initialize the algorithm with the given information and runner.

param info:

Information object containing algorithm and base parameters.

type info:

Info

param runner:

Optional runner object to execute the algorithm.

type runner:

Runner (optional)

param run_mode:

Mode in which the algorithm should run.

type run_mode:

str

abstractmethod __init__(info: Info, runner: Runner | None = None, run_mode: str = 'initial') None[source]#

Initialize the algorithm with the given information and runner.

Parameters:
  • info (Info) – Information object containing algorithm and base parameters.

  • runner (Runner (optional)) – Optional runner object to execute the algorithm.

  • run_mode (str) – Mode in which the algorithm should run.

__init_rng(info: Info) None#

Initialize the random number generator.

Parameters:

info (Info) – Information object containing algorithm parameters.

_apply_state(data: dict, mode: str = 'resume', restore_rng: bool = True) None[source]#

Restore the base algorithm state from a checkpoint snapshot.

Validates the MPI configuration, restores the timer, checks that algorithm parameters are consistent, and restores the RNG state. Subclasses should call super()._apply_state(data, mode=mode, restore_rng=restore_rng) and then handle their own subclass-specific fields (_checkpoint_attrs, continue-mode semantics, etc.). The RNG state saved by __getstate__ for every algorithm is restored here (guarded by restore_rng), so subclasses need not repeat it.

Parameters:
  • data (dict) – Snapshot previously produced by __getstate__.

  • mode (str) – "resume" or "continue". Passed through to subclass overrides so they can implement continue-mode semantics.

  • restore_rng (bool) – When True (default) the RNG state is restored from data.

_check_parameters(param=None)[source]#

Check the parameters of the algorithm against previous parameters.

Parameters:

(optional) (param) – Previous parameters to check against.

abstractmethod _initialize() None[source]#

Set up initial algorithm state for a fresh run (init mode).

Called by prepare() when mode starts with "init". Must not use the runner (evaluation happens later in _run()).

_load_data(filename='state.pickle') dict[source]#

Load data from a file.

Parameters:

filename – Name of the file to load the data from.

Returns:

Dictionary containing the loaded data.

Return type:

dict

_load_state(filename, mode='resume', restore_rng=True) None[source]#

Load a checkpoint snapshot from filename and apply it.

Delegates to _load_data() then _apply_state().

Override in subclasses only when extra files must be read (e.g. an external policy object). In that case call super()._load_state(filename, mode=mode, restore_rng=restore_rng) first.

Parameters:
  • filename (str) – Path to the checkpoint file.

  • mode (str) – "resume" or "continue", forwarded to _apply_state().

  • restore_rng (bool) – Whether to restore the RNG state.

abstractmethod _post() dict[source]#

Perform post-processing and return results.

abstractmethod _prepare() None[source]#

Algorithm-specific preparation, called after dispatch.

Override in subclasses to perform setup that must happen after the checkpoint state is established (e.g. initialising timer entries).

_reach_consensus(error: Exception | None, ok: ndarray) None[source]#

Collectively agree on whether every algorithm rank succeeded.

Every algorithm rank must call this exactly once per phase, regardless of whether its phase body succeeded or raised. ok is [1] when this rank’s phase succeeded and [0] otherwise; error is the exception this rank caught (or None).

A single Allreduce shares the success flags, then:

  • if this rank failed, its own exception is re-raised;

  • else if any other rank failed, OtherAlgorithmProcessError is raised so this rank bails out too.

Because the only collective on the failure path is this one Allreduce – reached by all ranks whether they succeeded or failed – a per-rank failure can no longer leave the other ranks blocked. (Collectives inside the _prepare/_run/_post hooks remain the responsibility of each algorithm to keep balanced across ranks.)

abstractmethod _run() None[source]#

Execute the main algorithm loop.

For init mode, perform the initial evaluation here before entering the main loop. Call _save_state() at the appropriate points inside the loop.

_save_data(data, filename='state.pickle', ngen=3) None[source]#

Save data to a file with versioning.

Parameters:
  • data – Data to be saved.

  • filename – Name of the file to save the data.

  • ngen (int, default: 3) – Number of generations for versioning.

_save_state(filename) None[source]#

Save a checkpoint snapshot to filename.

Uses __getstate__() to collect all fields declared in _checkpoint_attrs across the MRO, then delegates to _save_data() for versioned pickle storage.

Override in subclasses only when extra files must be written alongside the pickle (e.g. an external policy object). In that case call super()._save_state(filename) first.

_show_parameters()[source]#

Show the parameters of the algorithm.

main()[source]#

Main method to execute the algorithm.

post() dict[source]#

Framework wrapper for the post phase.

Calls the _post() hook then runner.post().

Do not override this method in subclasses. Implement _post() instead.

prepare() None[source]#

Framework wrapper for the prepare phase.

Calls runner.prepare(), dispatches init/resume/continue, then calls the _prepare() hook.

Do not override this method in subclasses. Implement _prepare() instead.

run() None[source]#

Framework wrapper for the run phase.

Calls the _run() hook. Runner calls are handled by prepare() and post(); this wrapper contains no runner invocations.

Do not override this method in subclasses. Implement _run() instead.

set_runner(runner: Runner) None[source]#

Set the runner for the algorithm.

Parameters:

runner (Runner) – Runner object to execute the algorithm.

write_timer(filename: Path)[source]#

Write the timing information to a file.

Parameters:

filename (Path) – Path to the file where timing information will be written.

class odatse.algorithm._algorithm.AlgorithmStatus(value)[source]#

Bases: IntEnum

Enumeration for the status of the algorithm.

odatse.algorithm._algorithm.flatten_dict(d, parent_key='', separator='.')[source]#

Flatten a nested dictionary.

Parameters:
  • d – Dictionary to flatten.

  • parent_key (str, default : "") – Key for the parent dictionary.

  • separator (str, default : ".") – Separator to use between keys.

Returns:

Flattened dictionary.

Return type:

dict