StochasticForceInference 2.0.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- SFI/__init__.py +64 -0
- SFI/bases/__init__.py +85 -0
- SFI/bases/constants.py +492 -0
- SFI/bases/linear.py +325 -0
- SFI/bases/monomials.py +218 -0
- SFI/bases/pairs.py +998 -0
- SFI/bases/spde.py +1537 -0
- SFI/diagnostics/__init__.py +60 -0
- SFI/diagnostics/assess.py +87 -0
- SFI/diagnostics/dynamics_order.py +621 -0
- SFI/diagnostics/plotting.py +226 -0
- SFI/diagnostics/report.py +238 -0
- SFI/diagnostics/residual_tests.py +395 -0
- SFI/diagnostics/residuals.py +688 -0
- SFI/inference/__init__.py +58 -0
- SFI/inference/base.py +1460 -0
- SFI/inference/optimizers.py +200 -0
- SFI/inference/overdamped.py +1214 -0
- SFI/inference/parametric_core/__init__.py +34 -0
- SFI/inference/parametric_core/covariance.py +232 -0
- SFI/inference/parametric_core/driver.py +272 -0
- SFI/inference/parametric_core/flow.py +149 -0
- SFI/inference/parametric_core/flow_multi.py +362 -0
- SFI/inference/parametric_core/flow_ud.py +168 -0
- SFI/inference/parametric_core/jacobians.py +540 -0
- SFI/inference/parametric_core/objective.py +286 -0
- SFI/inference/parametric_core/objective_ud.py +253 -0
- SFI/inference/parametric_core/precision.py +229 -0
- SFI/inference/parametric_core/solve.py +763 -0
- SFI/inference/result.py +362 -0
- SFI/inference/serialization.py +245 -0
- SFI/inference/sparse/__init__.py +67 -0
- SFI/inference/sparse/base.py +43 -0
- SFI/inference/sparse/beam.py +303 -0
- SFI/inference/sparse/greedy.py +151 -0
- SFI/inference/sparse/hillclimb.py +307 -0
- SFI/inference/sparse/lasso.py +178 -0
- SFI/inference/sparse/metrics.py +78 -0
- SFI/inference/sparse/result.py +278 -0
- SFI/inference/sparse/scorer.py +323 -0
- SFI/inference/sparse/stlsq.py +165 -0
- SFI/inference/sparsity.py +40 -0
- SFI/inference/underdamped.py +1355 -0
- SFI/integrate/__init__.py +38 -0
- SFI/integrate/api.py +920 -0
- SFI/integrate/integrand.py +402 -0
- SFI/integrate/rk4.py +156 -0
- SFI/integrate/timeops.py +174 -0
- SFI/langevin/__init__.py +29 -0
- SFI/langevin/base.py +863 -0
- SFI/langevin/chunked.py +225 -0
- SFI/langevin/noise.py +446 -0
- SFI/langevin/overdamped.py +560 -0
- SFI/langevin/underdamped.py +448 -0
- SFI/statefunc/__init__.py +49 -0
- SFI/statefunc/basis.py +87 -0
- SFI/statefunc/core/runtime.py +47 -0
- SFI/statefunc/factory.py +346 -0
- SFI/statefunc/interactor.py +90 -0
- SFI/statefunc/layout/__init__.py +29 -0
- SFI/statefunc/layout/_base.py +186 -0
- SFI/statefunc/layout/_eval_compiler.py +453 -0
- SFI/statefunc/layout/_fd_atoms.py +196 -0
- SFI/statefunc/layout/_grid.py +878 -0
- SFI/statefunc/layout/_sectors.py +166 -0
- SFI/statefunc/memhint.py +222 -0
- SFI/statefunc/nodes/__init__.py +56 -0
- SFI/statefunc/nodes/base.py +318 -0
- SFI/statefunc/nodes/contract.py +422 -0
- SFI/statefunc/nodes/interactions/__init__.py +23 -0
- SFI/statefunc/nodes/interactions/dispatcher.py +1365 -0
- SFI/statefunc/nodes/interactions/prepare.py +161 -0
- SFI/statefunc/nodes/interactions/specs.py +362 -0
- SFI/statefunc/nodes/interactions/stencils.py +718 -0
- SFI/statefunc/nodes/leaf.py +530 -0
- SFI/statefunc/nodes/ops/__init__.py +27 -0
- SFI/statefunc/nodes/ops/concat.py +28 -0
- SFI/statefunc/nodes/ops/derivative.py +447 -0
- SFI/statefunc/nodes/ops/einsum.py +120 -0
- SFI/statefunc/nodes/ops/linear.py +153 -0
- SFI/statefunc/nodes/ops/mapn.py +138 -0
- SFI/statefunc/nodes/ops/reshape_rank.py +158 -0
- SFI/statefunc/nodes/ops/slice.py +83 -0
- SFI/statefunc/params.py +309 -0
- SFI/statefunc/psf.py +112 -0
- SFI/statefunc/sf.py +104 -0
- SFI/statefunc/stateexpr.py +1243 -0
- SFI/statefunc/structexpr.py +1003 -0
- SFI/trajectory/__init__.py +31 -0
- SFI/trajectory/collection.py +1122 -0
- SFI/trajectory/dataset.py +1164 -0
- SFI/trajectory/degrade.py +1108 -0
- SFI/trajectory/io.py +1027 -0
- SFI/trajectory/reserved_extras.py +129 -0
- SFI/utils/__init__.py +17 -0
- SFI/utils/formatting.py +308 -0
- SFI/utils/maths.py +185 -0
- SFI/utils/neighbors.py +162 -0
- SFI/utils/plotting.py +1936 -0
- stochasticforceinference-2.0.0.dist-info/METADATA +203 -0
- stochasticforceinference-2.0.0.dist-info/RECORD +104 -0
- stochasticforceinference-2.0.0.dist-info/WHEEL +5 -0
- stochasticforceinference-2.0.0.dist-info/licenses/LICENSE +21 -0
- stochasticforceinference-2.0.0.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,60 @@
|
|
|
1
|
+
"""SFI diagnostics — residual-consistency checks for inference results.
|
|
2
|
+
|
|
3
|
+
Top-level user-facing entry point::
|
|
4
|
+
|
|
5
|
+
from SFI.diagnostics import assess
|
|
6
|
+
report = assess(inferer, level="standard")
|
|
7
|
+
report.print_summary()
|
|
8
|
+
|
|
9
|
+
The module reuses the fitted force and the inferred constant diffusion to
|
|
10
|
+
recompute standardised residuals (innovations) and test whether they look
|
|
11
|
+
like an independent ``N(0, 1)`` sample:
|
|
12
|
+
|
|
13
|
+
* mean, variance, skewness and kurtosis (pooled and per spatial
|
|
14
|
+
component), plus the per-component covariance;
|
|
15
|
+
* Ljung--Box autocorrelation of the residuals and their squares;
|
|
16
|
+
* Kolmogorov--Smirnov normality against ``N(0, 1)``;
|
|
17
|
+
* predicted-vs-realised normalised mean squared error of the force
|
|
18
|
+
(a sampling-noise-aware chi-square check).
|
|
19
|
+
|
|
20
|
+
See :mod:`SFI.diagnostics.residual_tests`. Two preset levels are exposed:
|
|
21
|
+
|
|
22
|
+
* ``"minimal"`` — residual moments only;
|
|
23
|
+
* ``"standard"`` — adds autocorrelation, normality, and MSE consistency.
|
|
24
|
+
|
|
25
|
+
All backends (overdamped / underdamped, single / multi-particle, SPDE)
|
|
26
|
+
share a unified residual definition: the Euler--Maruyama innovation
|
|
27
|
+
:math:`r_t = \\Delta x_t - F(x_t)\\,\\Delta t` (overdamped) or the
|
|
28
|
+
secant-velocity innovation
|
|
29
|
+
:math:`r_t = \\Delta v_t - F(x_t, v_t)\\,\\Delta t` (underdamped), both
|
|
30
|
+
whitened by :math:`(2 \\bar D \\Delta t)^{-1/2}`.
|
|
31
|
+
|
|
32
|
+
References
|
|
33
|
+
----------
|
|
34
|
+
Ljung & Box (1978); Diebold, Gunther & Tay (1998).
|
|
35
|
+
"""
|
|
36
|
+
|
|
37
|
+
from .assess import assess
|
|
38
|
+
from .dynamics_order import DynamicsOrderReport, classify_dynamics
|
|
39
|
+
from .plotting import (
|
|
40
|
+
plot_dynamics_order,
|
|
41
|
+
plot_qq,
|
|
42
|
+
plot_residual_acf,
|
|
43
|
+
plot_residual_histogram,
|
|
44
|
+
plot_summary,
|
|
45
|
+
)
|
|
46
|
+
from .report import DiagnosticsReport
|
|
47
|
+
from .residual_tests import parametric_four_point_diagnostic
|
|
48
|
+
|
|
49
|
+
__all__ = [
|
|
50
|
+
"assess",
|
|
51
|
+
"classify_dynamics",
|
|
52
|
+
"DiagnosticsReport",
|
|
53
|
+
"DynamicsOrderReport",
|
|
54
|
+
"parametric_four_point_diagnostic",
|
|
55
|
+
"plot_dynamics_order",
|
|
56
|
+
"plot_qq",
|
|
57
|
+
"plot_residual_acf",
|
|
58
|
+
"plot_residual_histogram",
|
|
59
|
+
"plot_summary",
|
|
60
|
+
]
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
"""Top-level diagnostic dispatcher.
|
|
2
|
+
|
|
3
|
+
See :func:`assess` for the user-facing entry point.
|
|
4
|
+
"""
|
|
5
|
+
|
|
6
|
+
from __future__ import annotations
|
|
7
|
+
|
|
8
|
+
from typing import Optional
|
|
9
|
+
|
|
10
|
+
from .report import DiagnosticsReport
|
|
11
|
+
from .residual_tests import (
|
|
12
|
+
autocorrelation_tests,
|
|
13
|
+
mse_consistency,
|
|
14
|
+
normality_test,
|
|
15
|
+
residual_moments,
|
|
16
|
+
)
|
|
17
|
+
from .residuals import build_residuals
|
|
18
|
+
|
|
19
|
+
_LEVELS = ("minimal", "standard")
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
def assess(
|
|
23
|
+
inferer,
|
|
24
|
+
*,
|
|
25
|
+
level: str = "standard",
|
|
26
|
+
n_lags: Optional[int] = None,
|
|
27
|
+
data=None,
|
|
28
|
+
) -> DiagnosticsReport:
|
|
29
|
+
"""Run residual-consistency checks on a fitted inference object.
|
|
30
|
+
|
|
31
|
+
Recomputes the standardised residuals (Euler--Maruyama innovations,
|
|
32
|
+
whitened by the inferred constant diffusion) and tests whether they
|
|
33
|
+
look like an independent ``N(0, 1)`` sample.
|
|
34
|
+
|
|
35
|
+
Parameters
|
|
36
|
+
----------
|
|
37
|
+
inferer :
|
|
38
|
+
A fitted ``OverdampedLangevinInference`` or
|
|
39
|
+
``UnderdampedLangevinInference``. Must have a callable
|
|
40
|
+
``force_inferred`` (run e.g. ``infer_force_linear`` first) and an
|
|
41
|
+
inferred constant diffusion (``A_inv``).
|
|
42
|
+
level :
|
|
43
|
+
``"minimal"`` — pooled residual moments only;
|
|
44
|
+
``"standard"`` (default) — adds autocorrelation, normality, and
|
|
45
|
+
predicted-vs-realised MSE consistency.
|
|
46
|
+
n_lags :
|
|
47
|
+
Number of autocorrelation lags. Default ``min(20, n_eff // 5)``.
|
|
48
|
+
data :
|
|
49
|
+
Optional independent :class:`~SFI.trajectory.TrajectoryCollection`
|
|
50
|
+
on which to evaluate the residuals (held-out diagnostics).
|
|
51
|
+
Default: the training data attached to the inferer.
|
|
52
|
+
|
|
53
|
+
Returns
|
|
54
|
+
-------
|
|
55
|
+
DiagnosticsReport
|
|
56
|
+
Container with a ``residuals`` section and ``meta``.
|
|
57
|
+
|
|
58
|
+
Notes
|
|
59
|
+
-----
|
|
60
|
+
The Euler-style residual is exact for the linear estimators; for the
|
|
61
|
+
parametric estimators it is an approximation that
|
|
62
|
+
is still asymptotically consistent under correct specification, so
|
|
63
|
+
the autocorrelation and normality tests remain valid for flagging
|
|
64
|
+
misspecification.
|
|
65
|
+
"""
|
|
66
|
+
if level not in _LEVELS:
|
|
67
|
+
raise ValueError(f"level must be one of {_LEVELS!r}; got {level!r}.")
|
|
68
|
+
|
|
69
|
+
bundle = build_residuals(inferer, data=data)
|
|
70
|
+
|
|
71
|
+
residuals: dict = {"moments": residual_moments(bundle)}
|
|
72
|
+
if level == "standard":
|
|
73
|
+
residuals["autocorr"] = autocorrelation_tests(bundle, n_lags=n_lags)
|
|
74
|
+
residuals["normality"] = normality_test(bundle)
|
|
75
|
+
residuals["mse_consistency"] = mse_consistency(inferer, bundle)
|
|
76
|
+
|
|
77
|
+
meta = {
|
|
78
|
+
"backend": bundle.backend,
|
|
79
|
+
"regime": bundle.regime,
|
|
80
|
+
"n_obs": bundle.n_obs,
|
|
81
|
+
"n_particles": bundle.n_particles,
|
|
82
|
+
"d": bundle.d,
|
|
83
|
+
"level": level,
|
|
84
|
+
"inferer_class": type(inferer).__name__,
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
return DiagnosticsReport(residuals=residuals, meta=meta)
|