Skip to content

Commit 118f471

Browse files
authored
introducing @register_dynamic decorator to solve dynamic-reuse issue (#1372)
1 parent f6b782c commit 118f471

File tree

23 files changed

+204
-95
lines changed

23 files changed

+204
-95
lines changed

PySDM/builder.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -121,8 +121,8 @@ def build(
121121
self._resolve_attribute(attr_name)
122122
self.req_attr_names = None
123123

124-
for dynamic in self.particulator.dynamics.values():
125-
dynamic.register(self)
124+
for key, dynamic in self.particulator.dynamics.items():
125+
self.particulator.dynamics[key] = dynamic.instantiate(builder=self)
126126

127127
single_buffer_for_all_products = np.empty(self.particulator.mesh.grid)
128128
for product in products:

PySDM/dynamics/ambient_thermodynamics.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,10 @@
22
environment-sync triggering class
33
"""
44

5+
from PySDM.dynamics.impl import register_dynamic
56

7+
8+
@register_dynamic()
69
class AmbientThermodynamics:
710
def __init__(self):
811
self.particulator = None

PySDM/dynamics/aqueous_chemistry.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,12 +13,14 @@
1313
M,
1414
SpecificGravities,
1515
)
16+
from PySDM.dynamics.impl import register_dynamic
1617

1718
DEFAULTS = namedtuple("_", ("pH_min", "pH_max", "pH_rtol", "ionic_strength_threshold"))(
1819
pH_min=-1.0, pH_max=14.0, pH_rtol=1e-6, ionic_strength_threshold=0.02 * M
1920
)
2021

2122

23+
@register_dynamic()
2224
class AqueousChemistry: # pylint: disable=too-many-instance-attributes
2325
def __init__(
2426
self,

PySDM/dynamics/collisions/collision.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@
2323
RandomGeneratorOptimizerNoPair,
2424
)
2525
from PySDM.physics import si
26+
from PySDM.dynamics.impl import register_dynamic
2627

2728
# pylint: disable=too-many-lines
2829

@@ -36,6 +37,7 @@
3637
)
3738

3839

40+
@register_dynamic()
3941
class Collision: # pylint: disable=too-many-instance-attributes
4042
def __init__(
4143
self,
@@ -288,6 +290,7 @@ def compute_gamma(self, prob, rand, is_first_in_pair, out):
288290
)
289291

290292

293+
@register_dynamic()
291294
class Coalescence(Collision):
292295
def __init__(
293296
self,
@@ -316,6 +319,7 @@ def __init__(
316319
)
317320

318321

322+
@register_dynamic()
319323
class Breakup(Collision):
320324
def __init__(
321325
self,

PySDM/dynamics/condensation.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,8 @@
77

88
import numpy as np
99

10-
from ..physics import si
10+
from PySDM.physics import si
11+
from PySDM.dynamics.impl import register_dynamic
1112

1213
DEFAULTS = namedtuple("_", ("rtol_x", "rtol_thd", "cond_range", "schedule"))(
1314
rtol_x=1e-6,
@@ -17,6 +18,7 @@
1718
)
1819

1920

21+
@register_dynamic()
2022
class Condensation: # pylint: disable=too-many-instance-attributes
2123
def __init__(
2224
self,

PySDM/dynamics/displacement.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,9 +11,12 @@
1111

1212
import numpy as np
1313

14+
from PySDM.dynamics.impl import register_dynamic
15+
1416
DEFAULTS = namedtuple("_", ("rtol", "adaptive"))(rtol=1e-2, adaptive=True)
1517

1618

19+
@register_dynamic()
1720
class Displacement: # pylint: disable=too-many-instance-attributes
1821
def __init__(
1922
self,

PySDM/dynamics/eulerian_advection.py

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,10 @@
22
wrapper class for triggering integration in the Eulerian advection solver
33
"""
44

5+
from PySDM.dynamics.impl import register_dynamic
56

7+
8+
@register_dynamic()
69
class EulerianAdvection:
710
def __init__(self, solvers):
811
self.solvers = solvers
@@ -12,12 +15,8 @@ def register(self, builder):
1215
self.particulator = builder.particulator
1316

1417
def __call__(self):
15-
self.particulator.environment.get_predicted(
16-
"water_vapour_mixing_ratio"
17-
).download(
18-
self.particulator.environment.get_water_vapour_mixing_ratio(), reshape=True
19-
)
20-
self.particulator.environment.get_predicted("thd").download(
21-
self.particulator.environment.get_thd(), reshape=True
22-
)
23-
self.solvers()
18+
for field in ("water_vapour_mixing_ratio", "thd"):
19+
self.particulator.environment.get_predicted(field).download(
20+
getattr(self.particulator.environment, f"get_{field}")(), reshape=True
21+
)
22+
self.solvers(self.particulator.dynamics["Displacement"])

PySDM/dynamics/freezing.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,10 @@
77
TimeDependentAttributes,
88
)
99
from PySDM.physics.heterogeneous_ice_nucleation_rate import Null
10+
from PySDM.dynamics.impl import register_dynamic
1011

1112

13+
@register_dynamic()
1214
class Freezing:
1315
def __init__(self, *, singular=True, record_freezing_temperature=False, thaw=False):
1416
assert not (record_freezing_temperature and singular)

PySDM/dynamics/impl/__init__.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,3 @@
11
""" stuff not intended to be imported from user code """
2+
3+
from .register_dynamic import register_dynamic
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
""" decorator for dynamics classes
2+
ensuring that their instances can be re-used with multiple builders """
3+
4+
from copy import deepcopy
5+
6+
7+
def _instantiate(self, *, builder):
8+
copy = deepcopy(self)
9+
copy.register(builder=builder)
10+
return copy
11+
12+
13+
def register_dynamic():
14+
def decorator(cls):
15+
if hasattr(cls, "instantiate"):
16+
assert cls.instantiate is _instantiate
17+
else:
18+
setattr(cls, "instantiate", _instantiate)
19+
return cls
20+
21+
return decorator

0 commit comments

Comments
 (0)