tnfr 3.0.3__py3-none-any.whl → 8.5.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.
Potentially problematic release.
This version of tnfr might be problematic. Click here for more details.
- tnfr/__init__.py +375 -56
- tnfr/__init__.pyi +33 -0
- tnfr/_compat.py +10 -0
- tnfr/_generated_version.py +34 -0
- tnfr/_version.py +49 -0
- tnfr/_version.pyi +7 -0
- tnfr/alias.py +723 -0
- tnfr/alias.pyi +108 -0
- tnfr/backends/__init__.py +354 -0
- tnfr/backends/jax_backend.py +173 -0
- tnfr/backends/numpy_backend.py +238 -0
- tnfr/backends/optimized_numpy.py +420 -0
- tnfr/backends/torch_backend.py +408 -0
- tnfr/cache.py +171 -0
- tnfr/cache.pyi +13 -0
- tnfr/cli/__init__.py +110 -0
- tnfr/cli/__init__.pyi +26 -0
- tnfr/cli/arguments.py +489 -0
- tnfr/cli/arguments.pyi +29 -0
- tnfr/cli/execution.py +914 -0
- tnfr/cli/execution.pyi +70 -0
- tnfr/cli/interactive_validator.py +614 -0
- tnfr/cli/utils.py +51 -0
- tnfr/cli/utils.pyi +7 -0
- tnfr/cli/validate.py +236 -0
- tnfr/compat/__init__.py +85 -0
- tnfr/compat/dataclass.py +136 -0
- tnfr/compat/jsonschema_stub.py +61 -0
- tnfr/compat/matplotlib_stub.py +73 -0
- tnfr/compat/numpy_stub.py +155 -0
- tnfr/config/__init__.py +224 -0
- tnfr/config/__init__.pyi +10 -0
- tnfr/config/constants.py +104 -0
- tnfr/config/constants.pyi +12 -0
- tnfr/config/defaults.py +54 -0
- tnfr/config/defaults_core.py +212 -0
- tnfr/config/defaults_init.py +33 -0
- tnfr/config/defaults_metric.py +104 -0
- tnfr/config/feature_flags.py +81 -0
- tnfr/config/feature_flags.pyi +16 -0
- tnfr/config/glyph_constants.py +31 -0
- tnfr/config/init.py +77 -0
- tnfr/config/init.pyi +8 -0
- tnfr/config/operator_names.py +254 -0
- tnfr/config/operator_names.pyi +36 -0
- tnfr/config/physics_derivation.py +354 -0
- tnfr/config/presets.py +83 -0
- tnfr/config/presets.pyi +7 -0
- tnfr/config/security.py +927 -0
- tnfr/config/thresholds.py +114 -0
- tnfr/config/tnfr_config.py +498 -0
- tnfr/constants/__init__.py +92 -0
- tnfr/constants/__init__.pyi +92 -0
- tnfr/constants/aliases.py +33 -0
- tnfr/constants/aliases.pyi +27 -0
- tnfr/constants/init.py +33 -0
- tnfr/constants/init.pyi +12 -0
- tnfr/constants/metric.py +104 -0
- tnfr/constants/metric.pyi +19 -0
- tnfr/core/__init__.py +33 -0
- tnfr/core/container.py +226 -0
- tnfr/core/default_implementations.py +329 -0
- tnfr/core/interfaces.py +279 -0
- tnfr/dynamics/__init__.py +238 -0
- tnfr/dynamics/__init__.pyi +83 -0
- tnfr/dynamics/adaptation.py +267 -0
- tnfr/dynamics/adaptation.pyi +7 -0
- tnfr/dynamics/adaptive_sequences.py +189 -0
- tnfr/dynamics/adaptive_sequences.pyi +14 -0
- tnfr/dynamics/aliases.py +23 -0
- tnfr/dynamics/aliases.pyi +19 -0
- tnfr/dynamics/bifurcation.py +232 -0
- tnfr/dynamics/canonical.py +229 -0
- tnfr/dynamics/canonical.pyi +48 -0
- tnfr/dynamics/coordination.py +385 -0
- tnfr/dynamics/coordination.pyi +25 -0
- tnfr/dynamics/dnfr.py +3034 -0
- tnfr/dynamics/dnfr.pyi +26 -0
- tnfr/dynamics/dynamic_limits.py +225 -0
- tnfr/dynamics/feedback.py +252 -0
- tnfr/dynamics/feedback.pyi +24 -0
- tnfr/dynamics/fused_dnfr.py +454 -0
- tnfr/dynamics/homeostasis.py +157 -0
- tnfr/dynamics/homeostasis.pyi +14 -0
- tnfr/dynamics/integrators.py +661 -0
- tnfr/dynamics/integrators.pyi +36 -0
- tnfr/dynamics/learning.py +310 -0
- tnfr/dynamics/learning.pyi +33 -0
- tnfr/dynamics/metabolism.py +254 -0
- tnfr/dynamics/nbody.py +796 -0
- tnfr/dynamics/nbody_tnfr.py +783 -0
- tnfr/dynamics/propagation.py +326 -0
- tnfr/dynamics/runtime.py +908 -0
- tnfr/dynamics/runtime.pyi +77 -0
- tnfr/dynamics/sampling.py +36 -0
- tnfr/dynamics/sampling.pyi +7 -0
- tnfr/dynamics/selectors.py +711 -0
- tnfr/dynamics/selectors.pyi +85 -0
- tnfr/dynamics/structural_clip.py +207 -0
- tnfr/errors/__init__.py +37 -0
- tnfr/errors/contextual.py +492 -0
- tnfr/execution.py +223 -0
- tnfr/execution.pyi +45 -0
- tnfr/extensions/__init__.py +205 -0
- tnfr/extensions/__init__.pyi +18 -0
- tnfr/extensions/base.py +173 -0
- tnfr/extensions/base.pyi +35 -0
- tnfr/extensions/business/__init__.py +71 -0
- tnfr/extensions/business/__init__.pyi +11 -0
- tnfr/extensions/business/cookbook.py +88 -0
- tnfr/extensions/business/cookbook.pyi +8 -0
- tnfr/extensions/business/health_analyzers.py +202 -0
- tnfr/extensions/business/health_analyzers.pyi +9 -0
- tnfr/extensions/business/patterns.py +183 -0
- tnfr/extensions/business/patterns.pyi +8 -0
- tnfr/extensions/medical/__init__.py +73 -0
- tnfr/extensions/medical/__init__.pyi +11 -0
- tnfr/extensions/medical/cookbook.py +88 -0
- tnfr/extensions/medical/cookbook.pyi +8 -0
- tnfr/extensions/medical/health_analyzers.py +181 -0
- tnfr/extensions/medical/health_analyzers.pyi +9 -0
- tnfr/extensions/medical/patterns.py +163 -0
- tnfr/extensions/medical/patterns.pyi +8 -0
- tnfr/flatten.py +262 -0
- tnfr/flatten.pyi +21 -0
- tnfr/gamma.py +354 -0
- tnfr/gamma.pyi +36 -0
- tnfr/glyph_history.py +377 -0
- tnfr/glyph_history.pyi +35 -0
- tnfr/glyph_runtime.py +19 -0
- tnfr/glyph_runtime.pyi +8 -0
- tnfr/immutable.py +218 -0
- tnfr/immutable.pyi +36 -0
- tnfr/initialization.py +203 -0
- tnfr/initialization.pyi +65 -0
- tnfr/io.py +10 -0
- tnfr/io.pyi +13 -0
- tnfr/locking.py +37 -0
- tnfr/locking.pyi +7 -0
- tnfr/mathematics/__init__.py +79 -0
- tnfr/mathematics/backend.py +453 -0
- tnfr/mathematics/backend.pyi +99 -0
- tnfr/mathematics/dynamics.py +408 -0
- tnfr/mathematics/dynamics.pyi +90 -0
- tnfr/mathematics/epi.py +391 -0
- tnfr/mathematics/epi.pyi +65 -0
- tnfr/mathematics/generators.py +242 -0
- tnfr/mathematics/generators.pyi +29 -0
- tnfr/mathematics/metrics.py +119 -0
- tnfr/mathematics/metrics.pyi +16 -0
- tnfr/mathematics/operators.py +239 -0
- tnfr/mathematics/operators.pyi +59 -0
- tnfr/mathematics/operators_factory.py +124 -0
- tnfr/mathematics/operators_factory.pyi +11 -0
- tnfr/mathematics/projection.py +87 -0
- tnfr/mathematics/projection.pyi +33 -0
- tnfr/mathematics/runtime.py +182 -0
- tnfr/mathematics/runtime.pyi +64 -0
- tnfr/mathematics/spaces.py +256 -0
- tnfr/mathematics/spaces.pyi +83 -0
- tnfr/mathematics/transforms.py +305 -0
- tnfr/mathematics/transforms.pyi +62 -0
- tnfr/metrics/__init__.py +79 -0
- tnfr/metrics/__init__.pyi +20 -0
- tnfr/metrics/buffer_cache.py +163 -0
- tnfr/metrics/buffer_cache.pyi +24 -0
- tnfr/metrics/cache_utils.py +214 -0
- tnfr/metrics/coherence.py +2009 -0
- tnfr/metrics/coherence.pyi +129 -0
- tnfr/metrics/common.py +158 -0
- tnfr/metrics/common.pyi +35 -0
- tnfr/metrics/core.py +316 -0
- tnfr/metrics/core.pyi +13 -0
- tnfr/metrics/diagnosis.py +833 -0
- tnfr/metrics/diagnosis.pyi +86 -0
- tnfr/metrics/emergence.py +245 -0
- tnfr/metrics/export.py +179 -0
- tnfr/metrics/export.pyi +7 -0
- tnfr/metrics/glyph_timing.py +379 -0
- tnfr/metrics/glyph_timing.pyi +81 -0
- tnfr/metrics/learning_metrics.py +280 -0
- tnfr/metrics/learning_metrics.pyi +21 -0
- tnfr/metrics/phase_coherence.py +351 -0
- tnfr/metrics/phase_compatibility.py +349 -0
- tnfr/metrics/reporting.py +183 -0
- tnfr/metrics/reporting.pyi +25 -0
- tnfr/metrics/sense_index.py +1203 -0
- tnfr/metrics/sense_index.pyi +9 -0
- tnfr/metrics/trig.py +373 -0
- tnfr/metrics/trig.pyi +13 -0
- tnfr/metrics/trig_cache.py +233 -0
- tnfr/metrics/trig_cache.pyi +10 -0
- tnfr/multiscale/__init__.py +32 -0
- tnfr/multiscale/hierarchical.py +517 -0
- tnfr/node.py +763 -0
- tnfr/node.pyi +139 -0
- tnfr/observers.py +255 -130
- tnfr/observers.pyi +31 -0
- tnfr/ontosim.py +144 -137
- tnfr/ontosim.pyi +28 -0
- tnfr/operators/__init__.py +1672 -0
- tnfr/operators/__init__.pyi +31 -0
- tnfr/operators/algebra.py +277 -0
- tnfr/operators/canonical_patterns.py +420 -0
- tnfr/operators/cascade.py +267 -0
- tnfr/operators/cycle_detection.py +358 -0
- tnfr/operators/definitions.py +4108 -0
- tnfr/operators/definitions.pyi +78 -0
- tnfr/operators/grammar.py +1164 -0
- tnfr/operators/grammar.pyi +140 -0
- tnfr/operators/hamiltonian.py +710 -0
- tnfr/operators/health_analyzer.py +809 -0
- tnfr/operators/jitter.py +272 -0
- tnfr/operators/jitter.pyi +11 -0
- tnfr/operators/lifecycle.py +314 -0
- tnfr/operators/metabolism.py +618 -0
- tnfr/operators/metrics.py +2138 -0
- tnfr/operators/network_analysis/__init__.py +27 -0
- tnfr/operators/network_analysis/source_detection.py +186 -0
- tnfr/operators/nodal_equation.py +395 -0
- tnfr/operators/pattern_detection.py +660 -0
- tnfr/operators/patterns.py +669 -0
- tnfr/operators/postconditions/__init__.py +38 -0
- tnfr/operators/postconditions/mutation.py +236 -0
- tnfr/operators/preconditions/__init__.py +1226 -0
- tnfr/operators/preconditions/coherence.py +305 -0
- tnfr/operators/preconditions/dissonance.py +236 -0
- tnfr/operators/preconditions/emission.py +128 -0
- tnfr/operators/preconditions/mutation.py +580 -0
- tnfr/operators/preconditions/reception.py +125 -0
- tnfr/operators/preconditions/resonance.py +364 -0
- tnfr/operators/registry.py +74 -0
- tnfr/operators/registry.pyi +9 -0
- tnfr/operators/remesh.py +1809 -0
- tnfr/operators/remesh.pyi +26 -0
- tnfr/operators/structural_units.py +268 -0
- tnfr/operators/unified_grammar.py +105 -0
- tnfr/parallel/__init__.py +54 -0
- tnfr/parallel/auto_scaler.py +234 -0
- tnfr/parallel/distributed.py +384 -0
- tnfr/parallel/engine.py +238 -0
- tnfr/parallel/gpu_engine.py +420 -0
- tnfr/parallel/monitoring.py +248 -0
- tnfr/parallel/partitioner.py +459 -0
- tnfr/py.typed +0 -0
- tnfr/recipes/__init__.py +22 -0
- tnfr/recipes/cookbook.py +743 -0
- tnfr/rng.py +178 -0
- tnfr/rng.pyi +26 -0
- tnfr/schemas/__init__.py +8 -0
- tnfr/schemas/grammar.json +94 -0
- tnfr/sdk/__init__.py +107 -0
- tnfr/sdk/__init__.pyi +19 -0
- tnfr/sdk/adaptive_system.py +173 -0
- tnfr/sdk/adaptive_system.pyi +21 -0
- tnfr/sdk/builders.py +370 -0
- tnfr/sdk/builders.pyi +51 -0
- tnfr/sdk/fluent.py +1121 -0
- tnfr/sdk/fluent.pyi +74 -0
- tnfr/sdk/templates.py +342 -0
- tnfr/sdk/templates.pyi +41 -0
- tnfr/sdk/utils.py +341 -0
- tnfr/secure_config.py +46 -0
- tnfr/security/__init__.py +70 -0
- tnfr/security/database.py +514 -0
- tnfr/security/subprocess.py +503 -0
- tnfr/security/validation.py +290 -0
- tnfr/selector.py +247 -0
- tnfr/selector.pyi +19 -0
- tnfr/sense.py +378 -0
- tnfr/sense.pyi +23 -0
- tnfr/services/__init__.py +17 -0
- tnfr/services/orchestrator.py +325 -0
- tnfr/sparse/__init__.py +39 -0
- tnfr/sparse/representations.py +492 -0
- tnfr/structural.py +705 -0
- tnfr/structural.pyi +83 -0
- tnfr/telemetry/__init__.py +35 -0
- tnfr/telemetry/cache_metrics.py +226 -0
- tnfr/telemetry/cache_metrics.pyi +64 -0
- tnfr/telemetry/nu_f.py +422 -0
- tnfr/telemetry/nu_f.pyi +108 -0
- tnfr/telemetry/verbosity.py +36 -0
- tnfr/telemetry/verbosity.pyi +15 -0
- tnfr/tokens.py +58 -0
- tnfr/tokens.pyi +36 -0
- tnfr/tools/__init__.py +20 -0
- tnfr/tools/domain_templates.py +478 -0
- tnfr/tools/sequence_generator.py +846 -0
- tnfr/topology/__init__.py +13 -0
- tnfr/topology/asymmetry.py +151 -0
- tnfr/trace.py +543 -0
- tnfr/trace.pyi +42 -0
- tnfr/tutorials/__init__.py +38 -0
- tnfr/tutorials/autonomous_evolution.py +285 -0
- tnfr/tutorials/interactive.py +1576 -0
- tnfr/tutorials/structural_metabolism.py +238 -0
- tnfr/types.py +775 -0
- tnfr/types.pyi +357 -0
- tnfr/units.py +68 -0
- tnfr/units.pyi +13 -0
- tnfr/utils/__init__.py +282 -0
- tnfr/utils/__init__.pyi +215 -0
- tnfr/utils/cache.py +4223 -0
- tnfr/utils/cache.pyi +470 -0
- tnfr/utils/callbacks.py +375 -0
- tnfr/utils/callbacks.pyi +49 -0
- tnfr/utils/chunks.py +108 -0
- tnfr/utils/chunks.pyi +22 -0
- tnfr/utils/data.py +428 -0
- tnfr/utils/data.pyi +74 -0
- tnfr/utils/graph.py +85 -0
- tnfr/utils/graph.pyi +10 -0
- tnfr/utils/init.py +821 -0
- tnfr/utils/init.pyi +80 -0
- tnfr/utils/io.py +559 -0
- tnfr/utils/io.pyi +66 -0
- tnfr/utils/numeric.py +114 -0
- tnfr/utils/numeric.pyi +21 -0
- tnfr/validation/__init__.py +257 -0
- tnfr/validation/__init__.pyi +85 -0
- tnfr/validation/compatibility.py +460 -0
- tnfr/validation/compatibility.pyi +6 -0
- tnfr/validation/config.py +73 -0
- tnfr/validation/graph.py +139 -0
- tnfr/validation/graph.pyi +18 -0
- tnfr/validation/input_validation.py +755 -0
- tnfr/validation/invariants.py +712 -0
- tnfr/validation/rules.py +253 -0
- tnfr/validation/rules.pyi +44 -0
- tnfr/validation/runtime.py +279 -0
- tnfr/validation/runtime.pyi +28 -0
- tnfr/validation/sequence_validator.py +162 -0
- tnfr/validation/soft_filters.py +170 -0
- tnfr/validation/soft_filters.pyi +32 -0
- tnfr/validation/spectral.py +164 -0
- tnfr/validation/spectral.pyi +42 -0
- tnfr/validation/validator.py +1266 -0
- tnfr/validation/window.py +39 -0
- tnfr/validation/window.pyi +1 -0
- tnfr/visualization/__init__.py +98 -0
- tnfr/visualization/cascade_viz.py +256 -0
- tnfr/visualization/hierarchy.py +284 -0
- tnfr/visualization/sequence_plotter.py +784 -0
- tnfr/viz/__init__.py +60 -0
- tnfr/viz/matplotlib.py +278 -0
- tnfr/viz/matplotlib.pyi +35 -0
- tnfr-8.5.0.dist-info/METADATA +573 -0
- tnfr-8.5.0.dist-info/RECORD +353 -0
- tnfr-8.5.0.dist-info/entry_points.txt +3 -0
- tnfr-3.0.3.dist-info/licenses/LICENSE.txt → tnfr-8.5.0.dist-info/licenses/LICENSE.md +1 -1
- tnfr/constants.py +0 -183
- tnfr/dynamics.py +0 -543
- tnfr/helpers.py +0 -198
- tnfr/main.py +0 -37
- tnfr/operators.py +0 -296
- tnfr-3.0.3.dist-info/METADATA +0 -35
- tnfr-3.0.3.dist-info/RECORD +0 -13
- {tnfr-3.0.3.dist-info → tnfr-8.5.0.dist-info}/WHEEL +0 -0
- {tnfr-3.0.3.dist-info → tnfr-8.5.0.dist-info}/top_level.txt +0 -0
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import numpy as np
|
|
4
|
+
from dataclasses import dataclass
|
|
5
|
+
from typing import Protocol
|
|
6
|
+
import numpy.typing as npt
|
|
7
|
+
|
|
8
|
+
__all__ = ["StateProjector", "BasicStateProjector"]
|
|
9
|
+
|
|
10
|
+
ComplexVector = npt.NDArray[np.complexfloating[np.float64, np.float64]]
|
|
11
|
+
|
|
12
|
+
class StateProjector(Protocol):
|
|
13
|
+
def __call__(
|
|
14
|
+
self,
|
|
15
|
+
epi: float,
|
|
16
|
+
nu_f: float,
|
|
17
|
+
theta: float,
|
|
18
|
+
dim: int,
|
|
19
|
+
rng: np.random.Generator | None = None,
|
|
20
|
+
) -> ComplexVector: ...
|
|
21
|
+
|
|
22
|
+
@dataclass
|
|
23
|
+
class BasicStateProjector:
|
|
24
|
+
dtype: np.dtype[np.complexfloating[np.float64, np.float64]] = ...
|
|
25
|
+
atol: float = ...
|
|
26
|
+
def __call__(
|
|
27
|
+
self,
|
|
28
|
+
epi: float,
|
|
29
|
+
nu_f: float,
|
|
30
|
+
theta: float,
|
|
31
|
+
dim: int,
|
|
32
|
+
rng: np.random.Generator | None = None,
|
|
33
|
+
) -> ComplexVector: ...
|
|
@@ -0,0 +1,182 @@
|
|
|
1
|
+
"""Runtime helpers capturing TNFR spectral performance metrics."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
from typing import Any, Sequence
|
|
6
|
+
|
|
7
|
+
import numpy as np
|
|
8
|
+
|
|
9
|
+
from ..config import get_flags
|
|
10
|
+
from ..utils import get_logger
|
|
11
|
+
from .backend import ensure_array, ensure_numpy, get_backend
|
|
12
|
+
from .operators import CoherenceOperator, FrequencyOperator
|
|
13
|
+
from .spaces import HilbertSpace
|
|
14
|
+
|
|
15
|
+
__all__ = [
|
|
16
|
+
"normalized",
|
|
17
|
+
"coherence",
|
|
18
|
+
"frequency_positive",
|
|
19
|
+
"stable_unitary",
|
|
20
|
+
"coherence_expectation",
|
|
21
|
+
"frequency_expectation",
|
|
22
|
+
]
|
|
23
|
+
|
|
24
|
+
LOGGER = get_logger(__name__)
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
def _as_vector(
|
|
28
|
+
state: Sequence[complex] | np.ndarray,
|
|
29
|
+
*,
|
|
30
|
+
dimension: int,
|
|
31
|
+
backend=None,
|
|
32
|
+
) -> Any:
|
|
33
|
+
resolved_backend = backend or get_backend()
|
|
34
|
+
vector = ensure_array(state, dtype=np.complex128, backend=resolved_backend)
|
|
35
|
+
if (
|
|
36
|
+
getattr(vector, "ndim", len(getattr(vector, "shape", ()))) != 1
|
|
37
|
+
or vector.shape[0] != dimension
|
|
38
|
+
):
|
|
39
|
+
raise ValueError(
|
|
40
|
+
"State vector dimension mismatch: "
|
|
41
|
+
f"expected ({dimension},), received {vector.shape!r}."
|
|
42
|
+
)
|
|
43
|
+
return vector
|
|
44
|
+
|
|
45
|
+
|
|
46
|
+
def _resolve_operator_backend(operator: CoherenceOperator) -> tuple[Any, Any]:
|
|
47
|
+
backend = getattr(operator, "backend", None) or get_backend()
|
|
48
|
+
matrix_backend = getattr(operator, "_matrix_backend", None)
|
|
49
|
+
if matrix_backend is None:
|
|
50
|
+
matrix_backend = ensure_array(
|
|
51
|
+
operator.matrix, dtype=np.complex128, backend=backend
|
|
52
|
+
)
|
|
53
|
+
return backend, matrix_backend
|
|
54
|
+
|
|
55
|
+
|
|
56
|
+
def _maybe_log(metric: str, payload: dict[str, object]) -> None:
|
|
57
|
+
if not get_flags().log_performance:
|
|
58
|
+
return
|
|
59
|
+
LOGGER.debug("%s: %s", metric, payload)
|
|
60
|
+
|
|
61
|
+
|
|
62
|
+
def normalized(
|
|
63
|
+
state: Sequence[complex] | np.ndarray,
|
|
64
|
+
hilbert_space: HilbertSpace,
|
|
65
|
+
*,
|
|
66
|
+
atol: float = 1e-9,
|
|
67
|
+
label: str = "state",
|
|
68
|
+
) -> tuple[bool, float]:
|
|
69
|
+
"""Return normalization status and norm for ``state``."""
|
|
70
|
+
|
|
71
|
+
backend = get_backend()
|
|
72
|
+
vector = _as_vector(state, dimension=hilbert_space.dimension, backend=backend)
|
|
73
|
+
norm_backend = backend.norm(vector)
|
|
74
|
+
norm = float(np.asarray(ensure_numpy(norm_backend, backend=backend)))
|
|
75
|
+
passed = bool(np.isclose(norm, 1.0, atol=atol))
|
|
76
|
+
_maybe_log("normalized", {"label": label, "norm": norm, "passed": passed})
|
|
77
|
+
return passed, float(norm)
|
|
78
|
+
|
|
79
|
+
|
|
80
|
+
def coherence_expectation(
|
|
81
|
+
state: Sequence[complex] | np.ndarray,
|
|
82
|
+
operator: CoherenceOperator,
|
|
83
|
+
*,
|
|
84
|
+
normalise: bool = True,
|
|
85
|
+
atol: float = 1e-9,
|
|
86
|
+
) -> float:
|
|
87
|
+
"""Return the coherence expectation value for ``state``."""
|
|
88
|
+
|
|
89
|
+
return float(operator.expectation(state, normalise=normalise, atol=atol))
|
|
90
|
+
|
|
91
|
+
|
|
92
|
+
def coherence(
|
|
93
|
+
state: Sequence[complex] | np.ndarray,
|
|
94
|
+
operator: CoherenceOperator,
|
|
95
|
+
threshold: float,
|
|
96
|
+
*,
|
|
97
|
+
normalise: bool = True,
|
|
98
|
+
atol: float = 1e-9,
|
|
99
|
+
label: str = "state",
|
|
100
|
+
) -> tuple[bool, float]:
|
|
101
|
+
"""Evaluate coherence expectation against ``threshold``."""
|
|
102
|
+
|
|
103
|
+
value = coherence_expectation(state, operator, normalise=normalise, atol=atol)
|
|
104
|
+
passed = bool(value + atol >= threshold)
|
|
105
|
+
_maybe_log(
|
|
106
|
+
"coherence",
|
|
107
|
+
{"label": label, "value": value, "threshold": threshold, "passed": passed},
|
|
108
|
+
)
|
|
109
|
+
return passed, value
|
|
110
|
+
|
|
111
|
+
|
|
112
|
+
def frequency_expectation(
|
|
113
|
+
state: Sequence[complex] | np.ndarray,
|
|
114
|
+
operator: FrequencyOperator,
|
|
115
|
+
*,
|
|
116
|
+
normalise: bool = True,
|
|
117
|
+
atol: float = 1e-9,
|
|
118
|
+
) -> float:
|
|
119
|
+
"""Return the structural frequency projection for ``state``."""
|
|
120
|
+
|
|
121
|
+
return float(operator.project_frequency(state, normalise=normalise, atol=atol))
|
|
122
|
+
|
|
123
|
+
|
|
124
|
+
def frequency_positive(
|
|
125
|
+
state: Sequence[complex] | np.ndarray,
|
|
126
|
+
operator: FrequencyOperator,
|
|
127
|
+
*,
|
|
128
|
+
normalise: bool = True,
|
|
129
|
+
enforce: bool = True,
|
|
130
|
+
atol: float = 1e-9,
|
|
131
|
+
label: str = "state",
|
|
132
|
+
) -> dict[str, float | bool]:
|
|
133
|
+
"""Return summary ensuring structural frequency remains non-negative."""
|
|
134
|
+
|
|
135
|
+
spectrum = operator.spectrum()
|
|
136
|
+
spectrum_psd = bool(operator.is_positive_semidefinite(atol=atol))
|
|
137
|
+
value = frequency_expectation(state, operator, normalise=normalise, atol=atol)
|
|
138
|
+
projection_ok = bool(value + atol >= 0.0)
|
|
139
|
+
passed = bool(spectrum_psd and (projection_ok or not enforce))
|
|
140
|
+
summary = {
|
|
141
|
+
"passed": passed,
|
|
142
|
+
"value": value,
|
|
143
|
+
"enforce": enforce,
|
|
144
|
+
"spectrum_psd": spectrum_psd,
|
|
145
|
+
"spectrum_min": float(np.min(spectrum)) if spectrum.size else float("inf"),
|
|
146
|
+
"projection_passed": projection_ok,
|
|
147
|
+
}
|
|
148
|
+
_maybe_log("frequency_positive", {"label": label, **summary})
|
|
149
|
+
return summary
|
|
150
|
+
|
|
151
|
+
|
|
152
|
+
def stable_unitary(
|
|
153
|
+
state: Sequence[complex] | np.ndarray,
|
|
154
|
+
operator: CoherenceOperator,
|
|
155
|
+
hilbert_space: HilbertSpace,
|
|
156
|
+
*,
|
|
157
|
+
normalise: bool = True,
|
|
158
|
+
atol: float = 1e-9,
|
|
159
|
+
label: str = "state",
|
|
160
|
+
) -> tuple[bool, float]:
|
|
161
|
+
"""Return whether a one-step unitary preserves the Hilbert norm."""
|
|
162
|
+
|
|
163
|
+
backend, matrix_backend = _resolve_operator_backend(operator)
|
|
164
|
+
vector = _as_vector(state, dimension=hilbert_space.dimension, backend=backend)
|
|
165
|
+
if normalise:
|
|
166
|
+
norm_backend = backend.norm(vector)
|
|
167
|
+
norm = float(np.asarray(ensure_numpy(norm_backend, backend=backend)))
|
|
168
|
+
if np.isclose(norm, 0.0, atol=atol):
|
|
169
|
+
raise ValueError("Cannot normalise a null state vector.")
|
|
170
|
+
vector = vector / norm
|
|
171
|
+
generator = -1j * matrix_backend
|
|
172
|
+
unitary = backend.matrix_exp(generator)
|
|
173
|
+
evolved_backend = backend.matmul(unitary, vector[..., None]).reshape(
|
|
174
|
+
(hilbert_space.dimension,)
|
|
175
|
+
)
|
|
176
|
+
evolved = np.asarray(ensure_numpy(evolved_backend, backend=backend))
|
|
177
|
+
norm_after = hilbert_space.norm(evolved)
|
|
178
|
+
passed = bool(np.isclose(norm_after, 1.0, atol=atol))
|
|
179
|
+
_maybe_log(
|
|
180
|
+
"stable_unitary", {"label": label, "norm_after": norm_after, "passed": passed}
|
|
181
|
+
)
|
|
182
|
+
return passed, float(norm_after)
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import numpy as np
|
|
4
|
+
from .operators import CoherenceOperator, FrequencyOperator
|
|
5
|
+
from .spaces import HilbertSpace
|
|
6
|
+
from typing import Sequence
|
|
7
|
+
|
|
8
|
+
__all__ = [
|
|
9
|
+
"normalized",
|
|
10
|
+
"coherence",
|
|
11
|
+
"frequency_positive",
|
|
12
|
+
"stable_unitary",
|
|
13
|
+
"coherence_expectation",
|
|
14
|
+
"frequency_expectation",
|
|
15
|
+
]
|
|
16
|
+
|
|
17
|
+
def normalized(
|
|
18
|
+
state: Sequence[complex] | np.ndarray,
|
|
19
|
+
hilbert_space: HilbertSpace,
|
|
20
|
+
*,
|
|
21
|
+
atol: float = 1e-09,
|
|
22
|
+
label: str = "state",
|
|
23
|
+
) -> tuple[bool, float]: ...
|
|
24
|
+
def coherence_expectation(
|
|
25
|
+
state: Sequence[complex] | np.ndarray,
|
|
26
|
+
operator: CoherenceOperator,
|
|
27
|
+
*,
|
|
28
|
+
normalise: bool = True,
|
|
29
|
+
atol: float = 1e-09,
|
|
30
|
+
) -> float: ...
|
|
31
|
+
def coherence(
|
|
32
|
+
state: Sequence[complex] | np.ndarray,
|
|
33
|
+
operator: CoherenceOperator,
|
|
34
|
+
threshold: float,
|
|
35
|
+
*,
|
|
36
|
+
normalise: bool = True,
|
|
37
|
+
atol: float = 1e-09,
|
|
38
|
+
label: str = "state",
|
|
39
|
+
) -> tuple[bool, float]: ...
|
|
40
|
+
def frequency_expectation(
|
|
41
|
+
state: Sequence[complex] | np.ndarray,
|
|
42
|
+
operator: FrequencyOperator,
|
|
43
|
+
*,
|
|
44
|
+
normalise: bool = True,
|
|
45
|
+
atol: float = 1e-09,
|
|
46
|
+
) -> float: ...
|
|
47
|
+
def frequency_positive(
|
|
48
|
+
state: Sequence[complex] | np.ndarray,
|
|
49
|
+
operator: FrequencyOperator,
|
|
50
|
+
*,
|
|
51
|
+
normalise: bool = True,
|
|
52
|
+
enforce: bool = True,
|
|
53
|
+
atol: float = 1e-09,
|
|
54
|
+
label: str = "state",
|
|
55
|
+
) -> dict[str, float | bool]: ...
|
|
56
|
+
def stable_unitary(
|
|
57
|
+
state: Sequence[complex] | np.ndarray,
|
|
58
|
+
operator: CoherenceOperator,
|
|
59
|
+
hilbert_space: HilbertSpace,
|
|
60
|
+
*,
|
|
61
|
+
normalise: bool = True,
|
|
62
|
+
atol: float = 1e-09,
|
|
63
|
+
label: str = "state",
|
|
64
|
+
) -> tuple[bool, float]: ...
|
|
@@ -0,0 +1,256 @@
|
|
|
1
|
+
"""Mathematical spaces supporting the TNFR canonical paradigm."""
|
|
2
|
+
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
from dataclasses import dataclass
|
|
6
|
+
from typing import Callable, Sequence
|
|
7
|
+
|
|
8
|
+
import numpy as np
|
|
9
|
+
|
|
10
|
+
from .epi import BEPIElement, _EPIValidators
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
@dataclass(frozen=True)
|
|
14
|
+
class HilbertSpace:
|
|
15
|
+
r"""Finite section of :math:`\ell^2(\mathbb{N}) \otimes L^2(\mathbb{R})`.
|
|
16
|
+
|
|
17
|
+
The space models the discrete spectral component of the TNFR paradigm. The
|
|
18
|
+
canonical orthonormal basis corresponds to the standard coordinate vectors
|
|
19
|
+
and the inner product is sesquilinear, implemented through
|
|
20
|
+
:func:`numpy.vdot`. Projection returns expansion coefficients for any
|
|
21
|
+
supplied orthonormal basis.
|
|
22
|
+
"""
|
|
23
|
+
|
|
24
|
+
dimension: int
|
|
25
|
+
dtype: np.dtype = np.complex128
|
|
26
|
+
|
|
27
|
+
def __post_init__(self) -> None:
|
|
28
|
+
if self.dimension <= 0:
|
|
29
|
+
raise ValueError("Hilbert spaces require a positive dimension.")
|
|
30
|
+
|
|
31
|
+
@property
|
|
32
|
+
def basis(self) -> np.ndarray:
|
|
33
|
+
"""Return the canonical orthonormal basis as identity vectors."""
|
|
34
|
+
|
|
35
|
+
return np.eye(self.dimension, dtype=self.dtype)
|
|
36
|
+
|
|
37
|
+
def _as_vector(self, value: Sequence[complex] | np.ndarray) -> np.ndarray:
|
|
38
|
+
vector = np.asarray(value, dtype=self.dtype)
|
|
39
|
+
if vector.shape != (self.dimension,):
|
|
40
|
+
raise ValueError(
|
|
41
|
+
f"Vector must have shape ({self.dimension},), got {vector.shape!r}."
|
|
42
|
+
)
|
|
43
|
+
return vector
|
|
44
|
+
|
|
45
|
+
def inner_product(
|
|
46
|
+
self,
|
|
47
|
+
vector_a: Sequence[complex] | np.ndarray,
|
|
48
|
+
vector_b: Sequence[complex] | np.ndarray,
|
|
49
|
+
) -> complex:
|
|
50
|
+
"""Compute the sesquilinear inner product ``⟨a, b⟩``."""
|
|
51
|
+
|
|
52
|
+
vec_a = self._as_vector(vector_a)
|
|
53
|
+
vec_b = self._as_vector(vector_b)
|
|
54
|
+
return np.vdot(vec_a, vec_b)
|
|
55
|
+
|
|
56
|
+
def norm(self, vector: Sequence[complex] | np.ndarray) -> float:
|
|
57
|
+
"""Return the Hilbert norm induced by the inner product."""
|
|
58
|
+
|
|
59
|
+
value = self.inner_product(vector, vector)
|
|
60
|
+
magnitude = max(value.real, 0.0)
|
|
61
|
+
return float(np.sqrt(magnitude))
|
|
62
|
+
|
|
63
|
+
def is_normalized(
|
|
64
|
+
self, vector: Sequence[complex] | np.ndarray, *, atol: float = 1e-9
|
|
65
|
+
) -> bool:
|
|
66
|
+
"""Check whether a vector has unit norm within a tolerance."""
|
|
67
|
+
|
|
68
|
+
return np.isclose(self.norm(vector), 1.0, atol=atol)
|
|
69
|
+
|
|
70
|
+
def _validate_basis(
|
|
71
|
+
self, basis: Sequence[Sequence[complex] | np.ndarray]
|
|
72
|
+
) -> np.ndarray:
|
|
73
|
+
basis_list = list(basis)
|
|
74
|
+
if len(basis_list) == 0:
|
|
75
|
+
raise ValueError("An orthonormal basis must contain at least one vector.")
|
|
76
|
+
|
|
77
|
+
basis_vectors = [self._as_vector(vector) for vector in basis_list]
|
|
78
|
+
matrix = np.vstack(basis_vectors)
|
|
79
|
+
gram = matrix @ matrix.conj().T
|
|
80
|
+
identity = np.eye(matrix.shape[0], dtype=self.dtype)
|
|
81
|
+
if not np.allclose(gram, identity, atol=1e-10):
|
|
82
|
+
raise ValueError("Provided basis is not orthonormal within tolerance.")
|
|
83
|
+
return matrix
|
|
84
|
+
|
|
85
|
+
def project(
|
|
86
|
+
self,
|
|
87
|
+
vector: Sequence[complex] | np.ndarray,
|
|
88
|
+
basis: Sequence[Sequence[complex] | np.ndarray] | None = None,
|
|
89
|
+
) -> np.ndarray:
|
|
90
|
+
"""Return coefficients ``⟨b_k|ψ⟩`` for the chosen orthonormal basis."""
|
|
91
|
+
|
|
92
|
+
vec = self._as_vector(vector)
|
|
93
|
+
if basis is None:
|
|
94
|
+
return vec.astype(self.dtype, copy=True)
|
|
95
|
+
|
|
96
|
+
basis_matrix = self._validate_basis(basis)
|
|
97
|
+
coefficients = basis_matrix.conj() @ vec
|
|
98
|
+
return coefficients.astype(self.dtype, copy=False)
|
|
99
|
+
|
|
100
|
+
|
|
101
|
+
class BanachSpaceEPI(_EPIValidators):
|
|
102
|
+
r"""Banach space for :math:`C^0([0, 1],\mathbb{C}) \oplus \ell^2(\mathbb{N})`.
|
|
103
|
+
|
|
104
|
+
Elements are represented by a pair ``(f, a)`` where ``f`` samples the
|
|
105
|
+
continuous field over a uniform grid ``x_grid`` and ``a`` is the discrete
|
|
106
|
+
spectral tail. The coherence norm combines the supremum of ``f``, the
|
|
107
|
+
:math:`\ell^2` norm of ``a`` and a derivative-based functional capturing
|
|
108
|
+
the local stability of ``f``.
|
|
109
|
+
"""
|
|
110
|
+
|
|
111
|
+
def element(
|
|
112
|
+
self,
|
|
113
|
+
f_continuous: Sequence[complex] | np.ndarray,
|
|
114
|
+
a_discrete: Sequence[complex] | np.ndarray,
|
|
115
|
+
*,
|
|
116
|
+
x_grid: Sequence[float] | np.ndarray,
|
|
117
|
+
) -> BEPIElement:
|
|
118
|
+
"""Create a :class:`~tnfr.mathematics.epi.BEPIElement` with validated data."""
|
|
119
|
+
|
|
120
|
+
self.validate_domain(f_continuous, a_discrete, x_grid)
|
|
121
|
+
return BEPIElement(f_continuous, a_discrete, x_grid)
|
|
122
|
+
|
|
123
|
+
def zero_element(
|
|
124
|
+
self,
|
|
125
|
+
*,
|
|
126
|
+
continuous_size: int,
|
|
127
|
+
discrete_size: int,
|
|
128
|
+
x_grid: Sequence[float] | np.ndarray | None = None,
|
|
129
|
+
) -> BEPIElement:
|
|
130
|
+
"""Return the neutral element for the direct sum."""
|
|
131
|
+
|
|
132
|
+
if continuous_size < 2:
|
|
133
|
+
raise ValueError("continuous_size must be at least two samples.")
|
|
134
|
+
grid = (
|
|
135
|
+
np.asarray(x_grid, dtype=float)
|
|
136
|
+
if x_grid is not None
|
|
137
|
+
else np.linspace(0.0, 1.0, continuous_size, dtype=float)
|
|
138
|
+
)
|
|
139
|
+
zeros_f = np.zeros(continuous_size, dtype=np.complex128)
|
|
140
|
+
zeros_a = np.zeros(discrete_size, dtype=np.complex128)
|
|
141
|
+
return self.element(zeros_f, zeros_a, x_grid=grid)
|
|
142
|
+
|
|
143
|
+
def canonical_basis(
|
|
144
|
+
self,
|
|
145
|
+
*,
|
|
146
|
+
continuous_size: int,
|
|
147
|
+
discrete_size: int,
|
|
148
|
+
continuous_index: int = 0,
|
|
149
|
+
discrete_index: int = 0,
|
|
150
|
+
x_grid: Sequence[float] | np.ndarray | None = None,
|
|
151
|
+
) -> BEPIElement:
|
|
152
|
+
"""Generate a canonical basis element for the Banach space."""
|
|
153
|
+
|
|
154
|
+
if continuous_size < 2:
|
|
155
|
+
raise ValueError("continuous_size must be at least two samples.")
|
|
156
|
+
if not (0 <= continuous_index < continuous_size):
|
|
157
|
+
raise ValueError("continuous_index out of range.")
|
|
158
|
+
if not (0 <= discrete_index < discrete_size):
|
|
159
|
+
raise ValueError("discrete_index out of range.")
|
|
160
|
+
|
|
161
|
+
grid = (
|
|
162
|
+
np.asarray(x_grid, dtype=float)
|
|
163
|
+
if x_grid is not None
|
|
164
|
+
else np.linspace(0.0, 1.0, continuous_size, dtype=float)
|
|
165
|
+
)
|
|
166
|
+
|
|
167
|
+
f_vector = np.zeros(continuous_size, dtype=np.complex128)
|
|
168
|
+
a_vector = np.zeros(discrete_size, dtype=np.complex128)
|
|
169
|
+
f_vector[continuous_index] = 1.0 + 0.0j
|
|
170
|
+
a_vector[discrete_index] = 1.0 + 0.0j
|
|
171
|
+
return self.element(f_vector, a_vector, x_grid=grid)
|
|
172
|
+
|
|
173
|
+
def direct_sum(self, left: BEPIElement, right: BEPIElement) -> BEPIElement:
|
|
174
|
+
"""Delegate direct sums to the underlying EPI element."""
|
|
175
|
+
|
|
176
|
+
return left.direct_sum(right)
|
|
177
|
+
|
|
178
|
+
def adjoint(self, element: BEPIElement) -> BEPIElement:
|
|
179
|
+
"""Return the adjoint element of the supplied operand."""
|
|
180
|
+
|
|
181
|
+
return element.adjoint()
|
|
182
|
+
|
|
183
|
+
def compose(
|
|
184
|
+
self,
|
|
185
|
+
element: BEPIElement,
|
|
186
|
+
transform: Callable[[np.ndarray], np.ndarray],
|
|
187
|
+
*,
|
|
188
|
+
spectral_transform: Callable[[np.ndarray], np.ndarray] | None = None,
|
|
189
|
+
) -> BEPIElement:
|
|
190
|
+
"""Compose an element with the provided transforms."""
|
|
191
|
+
|
|
192
|
+
return element.compose(transform, spectral_transform=spectral_transform)
|
|
193
|
+
|
|
194
|
+
def tensor_with_hilbert(
|
|
195
|
+
self,
|
|
196
|
+
element: BEPIElement,
|
|
197
|
+
hilbert_space: HilbertSpace,
|
|
198
|
+
vector: Sequence[complex] | np.ndarray | None = None,
|
|
199
|
+
) -> np.ndarray:
|
|
200
|
+
"""Compute the tensor product against a :class:`HilbertSpace` vector."""
|
|
201
|
+
|
|
202
|
+
raw_vector = hilbert_space.basis[0] if vector is None else vector
|
|
203
|
+
hilbert_vector = hilbert_space._as_vector(
|
|
204
|
+
raw_vector
|
|
205
|
+
) # pylint: disable=protected-access
|
|
206
|
+
return element.tensor(hilbert_vector)
|
|
207
|
+
|
|
208
|
+
def compute_coherence_functional(
|
|
209
|
+
self,
|
|
210
|
+
f_continuous: Sequence[complex] | np.ndarray,
|
|
211
|
+
x_grid: Sequence[float] | np.ndarray,
|
|
212
|
+
) -> float:
|
|
213
|
+
r"""Approximate :math:`\int |f'|^2 dx / (1 + \int |f|^2 dx)`."""
|
|
214
|
+
|
|
215
|
+
f_array, _, grid = self.validate_domain(
|
|
216
|
+
f_continuous, np.array([0.0], dtype=np.complex128), x_grid
|
|
217
|
+
)
|
|
218
|
+
if grid is None:
|
|
219
|
+
raise ValueError("x_grid must be provided for coherence evaluations.")
|
|
220
|
+
|
|
221
|
+
derivative = np.gradient(
|
|
222
|
+
f_array,
|
|
223
|
+
grid,
|
|
224
|
+
edge_order=2 if f_array.size > 2 else 1,
|
|
225
|
+
)
|
|
226
|
+
numerator = np.trapz(np.abs(derivative) ** 2, grid)
|
|
227
|
+
denominator = 1.0 + np.trapz(np.abs(f_array) ** 2, grid)
|
|
228
|
+
if denominator <= 0:
|
|
229
|
+
raise ValueError("Denominator of coherence functional must be positive.")
|
|
230
|
+
return float(np.real_if_close(numerator / denominator))
|
|
231
|
+
|
|
232
|
+
def coherence_norm(
|
|
233
|
+
self,
|
|
234
|
+
f_continuous: Sequence[complex] | np.ndarray,
|
|
235
|
+
a_discrete: Sequence[complex] | np.ndarray,
|
|
236
|
+
*,
|
|
237
|
+
x_grid: Sequence[float] | np.ndarray,
|
|
238
|
+
alpha: float = 1.0,
|
|
239
|
+
beta: float = 1.0,
|
|
240
|
+
gamma: float = 1.0,
|
|
241
|
+
) -> float:
|
|
242
|
+
"""Return ``α‖f‖_∞ + β‖a‖_2 + γ CF(f)`` for positive weights."""
|
|
243
|
+
|
|
244
|
+
if alpha <= 0 or beta <= 0 or gamma <= 0:
|
|
245
|
+
raise ValueError("alpha, beta and gamma must be strictly positive.")
|
|
246
|
+
|
|
247
|
+
f_array, a_array, grid = self.validate_domain(f_continuous, a_discrete, x_grid)
|
|
248
|
+
if grid is None:
|
|
249
|
+
raise ValueError("x_grid must be supplied when evaluating the norm.")
|
|
250
|
+
|
|
251
|
+
sup_norm = float(np.max(np.abs(f_array))) if f_array.size else 0.0
|
|
252
|
+
l2_norm = float(np.linalg.norm(a_array))
|
|
253
|
+
coherence_functional = self.compute_coherence_functional(f_array, grid)
|
|
254
|
+
|
|
255
|
+
value = alpha * sup_norm + beta * l2_norm + gamma * coherence_functional
|
|
256
|
+
return float(np.real_if_close(value))
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
from __future__ import annotations
|
|
2
|
+
|
|
3
|
+
import numpy as np
|
|
4
|
+
from .epi import BEPIElement as BEPIElement, _EPIValidators
|
|
5
|
+
from dataclasses import dataclass
|
|
6
|
+
from typing import Callable, Sequence
|
|
7
|
+
|
|
8
|
+
@dataclass(frozen=True)
|
|
9
|
+
class HilbertSpace:
|
|
10
|
+
dimension: int
|
|
11
|
+
dtype: np.dtype = ...
|
|
12
|
+
def __post_init__(self) -> None: ...
|
|
13
|
+
@property
|
|
14
|
+
def basis(self) -> np.ndarray: ...
|
|
15
|
+
def inner_product(
|
|
16
|
+
self,
|
|
17
|
+
vector_a: Sequence[complex] | np.ndarray,
|
|
18
|
+
vector_b: Sequence[complex] | np.ndarray,
|
|
19
|
+
) -> complex: ...
|
|
20
|
+
def norm(self, vector: Sequence[complex] | np.ndarray) -> float: ...
|
|
21
|
+
def is_normalized(
|
|
22
|
+
self, vector: Sequence[complex] | np.ndarray, *, atol: float = 1e-09
|
|
23
|
+
) -> bool: ...
|
|
24
|
+
def project(
|
|
25
|
+
self,
|
|
26
|
+
vector: Sequence[complex] | np.ndarray,
|
|
27
|
+
basis: Sequence[Sequence[complex] | np.ndarray] | None = None,
|
|
28
|
+
) -> np.ndarray: ...
|
|
29
|
+
|
|
30
|
+
class BanachSpaceEPI(_EPIValidators):
|
|
31
|
+
def element(
|
|
32
|
+
self,
|
|
33
|
+
f_continuous: Sequence[complex] | np.ndarray,
|
|
34
|
+
a_discrete: Sequence[complex] | np.ndarray,
|
|
35
|
+
*,
|
|
36
|
+
x_grid: Sequence[float] | np.ndarray,
|
|
37
|
+
) -> BEPIElement: ...
|
|
38
|
+
def zero_element(
|
|
39
|
+
self,
|
|
40
|
+
*,
|
|
41
|
+
continuous_size: int,
|
|
42
|
+
discrete_size: int,
|
|
43
|
+
x_grid: Sequence[float] | np.ndarray | None = None,
|
|
44
|
+
) -> BEPIElement: ...
|
|
45
|
+
def canonical_basis(
|
|
46
|
+
self,
|
|
47
|
+
*,
|
|
48
|
+
continuous_size: int,
|
|
49
|
+
discrete_size: int,
|
|
50
|
+
continuous_index: int = 0,
|
|
51
|
+
discrete_index: int = 0,
|
|
52
|
+
x_grid: Sequence[float] | np.ndarray | None = None,
|
|
53
|
+
) -> BEPIElement: ...
|
|
54
|
+
def direct_sum(self, left: BEPIElement, right: BEPIElement) -> BEPIElement: ...
|
|
55
|
+
def adjoint(self, element: BEPIElement) -> BEPIElement: ...
|
|
56
|
+
def compose(
|
|
57
|
+
self,
|
|
58
|
+
element: BEPIElement,
|
|
59
|
+
transform: Callable[[np.ndarray], np.ndarray],
|
|
60
|
+
*,
|
|
61
|
+
spectral_transform: Callable[[np.ndarray], np.ndarray] | None = None,
|
|
62
|
+
) -> BEPIElement: ...
|
|
63
|
+
def tensor_with_hilbert(
|
|
64
|
+
self,
|
|
65
|
+
element: BEPIElement,
|
|
66
|
+
hilbert_space: HilbertSpace,
|
|
67
|
+
vector: Sequence[complex] | np.ndarray | None = None,
|
|
68
|
+
) -> np.ndarray: ...
|
|
69
|
+
def compute_coherence_functional(
|
|
70
|
+
self,
|
|
71
|
+
f_continuous: Sequence[complex] | np.ndarray,
|
|
72
|
+
x_grid: Sequence[float] | np.ndarray,
|
|
73
|
+
) -> float: ...
|
|
74
|
+
def coherence_norm(
|
|
75
|
+
self,
|
|
76
|
+
f_continuous: Sequence[complex] | np.ndarray,
|
|
77
|
+
a_discrete: Sequence[complex] | np.ndarray,
|
|
78
|
+
*,
|
|
79
|
+
x_grid: Sequence[float] | np.ndarray,
|
|
80
|
+
alpha: float = 1.0,
|
|
81
|
+
beta: float = 1.0,
|
|
82
|
+
gamma: float = 1.0,
|
|
83
|
+
) -> float: ...
|