Add axis-aware parameter values#189
Conversation
5d72ef6 to
a3a1711
Compare
a3a1711 to
0fbccdf
Compare
|
Here is my suggested chunking of this PR to make it more reviewable — no comments on code content yet. The 5 PRs follow the natural seams of the implementation and can land sequentially without blocking work: PR 1 — PR 2 — Structured parameter contract PR 3 — System-declared contracts PR 4 — Engine/Simulator wiring + CLI PR 5 — Examples, docs, and integration test Each PR is ~300–470 lines and touches a single concept. Happy to discuss the boundaries further if any of these feel awkward to split out. |
jc-macdonald
left a comment
There was a problem hiding this comment.
see comment above for my suggestions on how to split this out/
pearsonca
left a comment
There was a problem hiding this comment.
Some notes. Still thinking thru this one.
There was a problem hiding this comment.
i actually think its important here to avoid depending on flepimop
There was a problem hiding this comment.
ibid previous comment; the point of the wrapper modules should be that I can use source which has no flepimop dependencies, but still works.
| } | ||
|
|
||
| simulator = Simulator.from_configuration_model(config_model, target=target) | ||
| initial_state, params = simulator.resolve_inputs() |
There was a problem hiding this comment.
definitely improvement in syntax here.
| @abstractmethod | ||
| def sample(self) -> Float64NDArray: | ||
| """Sample a value from the parameter. | ||
| def sample( |
There was a problem hiding this comment.
so in terms of MVP, i think this update + the definition of Axes is approximately all that's needed for the first stage.
i'm a little unclear on what request is doing here - feels like "axes" should define what the shape is?
say a parameter is a function of age and vaccination status. then the supplied axes should cover how the parameter is broken down.
|
|
||
| def __call__( | ||
| self, time: np.float64, state: Float64NDArray, **kwargs: Any | ||
| self, time: np.float64, state: Float64NDArray, **kwargs: ParameterValue |
There was a problem hiding this comment.
This approach seems fine for now, but i think we'd ultimately prefer ParameterValue to be more of an internal element, and let users have more flexibility in their parameter type choice.
This defines the API they have to meet; might be we want to place the shim here, but maybe not.
| """ | ||
| return self._stepper(time, state, **params) | ||
|
|
||
| def requested_parameters( |
There was a problem hiding this comment.
i think this becomes an abstract - this particular approach would work for adapter or wrapper modules, but probably something else for op_system
This changes the `Simulator` class to treat parameters as structured, axis-aware values rather than raw scalars or arrays. Systems now declare the parameter and model-state they need, parameters resolve against named axes at runtime, and engines receive structured initial conditions and parameters without hard-coded assumptions about state shape. - Added `flepimop2.axis` module to represent axis/collection of axis. - Changed `ParameterABC.sample()` to return frozen `ParameterValue` objects with resolved shape and values. - Placed developer-facing parameter related types under the `flepimop2.parameter.abc` subpackage. - Added `SystemABC.requested_parameters()/model_state()` methods to request parameters needed for the stepper or declare internal model state, namely initial conditions. - Kept initial conditions under parameters and represent model state as ordered parameter keys via `ModelStateSpecification`. - `ParameterValue` objects are now passed through simulator/engine/system so steppers can unwrap and manipulate the parameter as needed. - Removed the legacy hard-coded s0/i0/r0 initial conditions in the `flepimop2 simulate` command. - Added helpers for continuous bins, bin edits, points from continous axis objects. - Updated wrapper assets, examples, docs, and tests to use the new structured parameter contract. Closes #115. Closes #133.
0fbccdf to
79cfa09
Compare
|
@pearsonca regarding your point about no flepi dependence I've been thinking about this kind of thing for a lot of my earthsytems and solver calibration work. if helpful here's this package I've started working on https://github.com/jcm-sci/trade-study. Probably also relevant to your |
This changes the
Simulatorclass to treat parameters as structured,axis-aware values rather than raw scalars or arrays. Systems now declare
the parameter and model-state they need, parameters resolve against
named axes at runtime, and engines receive structured initial conditions
and parameters without hard-coded assumptions about state shape.
flepimop2.axismodule to represent axis/collection of axis.ParameterABC.sample()to return frozenParameterValueobjects with resolved shape and values.
flepimop2.parameter.abcsubpackage.SystemABC.requested_parameters()/model_state()methods torequest parameters needed for the stepper or declare internal model
state, namely initial conditions.
ordered parameter keys via
ModelStateSpecification.ParameterValueobjects are now passed throughsimulator/engine/system so steppers can unwrap and manipulate the
parameter as needed.
flepimop2 simulatecommand.axis objects.
structured parameter contract.
Closes #115. Closes #133.