Coverage for physioblocks / library / functions / watchers.py: 94%
34 statements
« prev ^ index » next coverage.py v7.13.1, created at 2026-01-09 16:40 +0100
« prev ^ index » next coverage.py v7.13.1, created at 2026-01-09 16:40 +0100
1# SPDX-FileCopyrightText: Copyright INRIA
2#
3# SPDX-License-Identifier: LGPL-3.0-only
4#
5# Copyright INRIA
6#
7# This file is part of PhysioBlocks, a library mostly developed by the
8# [Ananke project-team](https://team.inria.fr/ananke) at INRIA.
9#
10# Authors:
11# - Colin Drieu
12# - Dominique Chapelle
13# - François Kimmig
14# - Philippe Moireau
15#
16# PhysioBlocks is free software: you can redistribute it and/or modify it under the
17# terms of the GNU Lesser General Public License as published by the Free Software
18# Foundation, version 3 of the License.
19#
20# PhysioBlocks is distributed in the hope that it will be useful, but WITHOUT ANY
21# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
22# PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.
23#
24# You should have received a copy of the GNU Lesser General Public License along with
25# PhysioBlocks. If not, see <https://www.gnu.org/licenses/>.
27"""
28Watcher are useful functions to use to set **Output Functions**
29in the configuration.
30"""
32from __future__ import annotations
34from collections.abc import Iterable
35from dataclasses import dataclass, field
36from typing import Any
38import numpy as np
40from physioblocks.base.operators import AbstractBaseOperators
41from physioblocks.computing.models import Block
42from physioblocks.computing.quantities import Quantity
43from physioblocks.registers.type_register import register_type
44from physioblocks.simulation import AbstractFunction
46# Quantity Watcher function type name
47WATCH_QUANTITY_TYPE_ID = "watch_quantity"
50@dataclass
51@register_type(WATCH_QUANTITY_TYPE_ID)
52class WatchQuantity(AbstractFunction, AbstractBaseOperators):
53 """
54 Return the current value of the watch quantity.
55 """
57 quantity: Quantity[Any]
58 """The quantities to watch"""
60 @property
61 def operation_value(self) -> Any:
62 """
63 Value used with base operators.
65 :return: the current evaluation of the function
66 :rtype: Any
67 """
68 return self.eval()
70 def eval(self) -> Any:
71 """Just return the watched quantity current value
73 :return: the watched quantity current value
74 :rtype: np.float64 | np.ndarray"""
75 return self.quantity.current
78# Sum Blocks Quantity function type name
79SUM_BLOCKS_QUANTITY_TYPE_ID = "sum_blocks_quantity"
82@dataclass
83@register_type(SUM_BLOCKS_QUANTITY_TYPE_ID)
84class SumBlocksQuantity(AbstractFunction, AbstractBaseOperators):
85 """Sum the current values of quantities with the given name
86 for each the blocks."""
88 quantity_id: str
89 """block local id of the quantity to sum"""
91 elements: Iterable[Block] = field(default_factory=list)
92 """the blocks holding the quantity to sum"""
94 @property
95 def operation_value(self) -> Any:
96 """
97 Value used with base operators.
99 :return: the current evaluation of the function
100 :rtype: Any
101 """
102 return self.eval()
104 def eval(self) -> Any:
105 """
106 Sum the quantities
108 :return: the sum of the quantities
109 :rtype: Any
110 """
111 return np.sum(
112 [getattr(block, self.quantity_id).current for block in self.elements]
113 )