99robust alternative.
1010"""
1111
12+ from abc import ABC
1213from copy import deepcopy
14+ from typing import Optional
15+
16+ import numpy as np
1317
1418from imod .common .interfaces .iregridpackage import IRegridPackage
19+ from imod .common .utilities .dataclass_type import DataclassType
1520from imod .mf6 .package import Package
21+ from imod .schemata import AllValueSchema , DimsSchema , DTypeSchema
22+ from imod .typing import GridDataArray
23+ from imod .util .regrid import RegridderWeightsCache
1624
1725
18- class Advection (Package , IRegridPackage ):
26+ class AdvectionBase (Package , IRegridPackage , ABC ):
1927 _pkg_id = "adv"
2028 _template = Package ._initialize_template (_pkg_id )
21-
22- def __init__ (self , scheme : str ):
23- dict_dataset = {"scheme" : scheme }
29+ _scheme : str
30+
31+ _init_schemata = {
32+ "ats_percel" : [
33+ DimsSchema (),
34+ DTypeSchema (np .floating ),
35+ AllValueSchema (">" , 0.0 ),
36+ ],
37+ }
38+
39+ def __init__ (self , ats_percel : Optional [float ] = None , validate : bool = True ):
40+ dict_dataset = {"scheme" : self ._scheme , "ats_percel" : ats_percel }
2441 super ().__init__ (dict_dataset )
42+ self ._validate_init_schemata (validate )
2543
2644 def _render (self , directory , pkgname , globaltimes , binary ):
27- scheme = self .dataset ["scheme" ].item ()
28- return self ._template .render ({"scheme" : scheme })
45+ render_dict = {}
46+ render_dict ["scheme" ] = self .dataset ["scheme" ].item ()
47+ if "ats_percel" in self .dataset and self ._valid (
48+ self .dataset ["ats_percel" ].item ()
49+ ):
50+ render_dict ["ats_percel" ] = self .dataset ["ats_percel" ].item ()
51+ return self ._template .render (render_dict )
2952
3053 def mask (self , _ ) -> Package :
3154 """
32- The mask method is irrelevant for this package , instead this method
55+ The mask method is irrelevant for this package, instead this method
56+ retuns a copy of itself.
57+ """
58+ return deepcopy (self )
59+
60+ def regrid_like (
61+ self ,
62+ target_grid : GridDataArray ,
63+ regrid_cache : RegridderWeightsCache ,
64+ regridder_types : Optional [DataclassType ] = None ,
65+ ) -> Package :
66+ """
67+ The regrid_like method is irrelevant for this package, instead this method
3368 retuns a copy of itself.
3469 """
3570 return deepcopy (self )
3671
3772
38- class AdvectionUpstream (Advection ):
73+ class AdvectionUpstream (AdvectionBase ):
3974 """
4075 The upstream weighting (first order upwind) scheme sets the concentration
4176 at the cellface between two adjacent cells equal to the concentration in
4277 the cell where the flow comes from. It surpresses oscillations.
43- Note: all constructor arguments will be ignored
78+
79+ Parameters
80+ ----------
81+ ats_percel: float, optional
82+ Fractional cell distance submitted by the ADV Package to the
83+ :class:`imod.mf6.AdaptiveTimeStepping` (ATS) package. If ``ats_percel``
84+ is specified and the ATS Package is active, a time step calculation will
85+ be made for each cell based on flow through the cell and cell
86+ properties. The largest time step will be calculated such that the
87+ advective fractional cell distance (``ats_percel``) is not exceeded for
88+ any active cell in the grid. This time-step constraint will be submitted
89+ to the ATS Package, perhaps with constraints submitted by other
90+ packages, in the calculation of the time step. ``ats_percel`` must be
91+ greater than zero. If a value of zero is specified for ``ats_percel``
92+ the program will automatically reset it to an internal no data value to
93+ indicate that time steps should not be subject to this constraint.
94+ Requires MODFLOW 6.6.0 or higher.
95+ validate: bool, optional
96+ Validate the package upon initialization. Defaults to True.
4497 """
4598
46- def __init__ (self , scheme : str = "upstream" ):
47- if not scheme == "upstream" :
48- raise ValueError (
49- "error in scheme parameter. Should be 'upstream' if present."
50- )
51- super ().__init__ (scheme = "upstream" )
99+ _scheme = "upstream"
52100
53101
54- class AdvectionCentral (Advection ):
102+ class AdvectionCentral (AdvectionBase ):
55103 """
56104 The central-in-space weighting scheme is based on a simple
57105 distance-weighted linear interpolation between the center of cell n and the
@@ -60,25 +108,53 @@ class AdvectionCentral(Advection):
60108 grids without equal spacing between connected cells, it is retained here
61109 for consistency with nomenclature used by other MODFLOW-based transport
62110 programs, such as MT3D.
63- Note: all constructor arguments will be ignored
111+
112+ Parameters
113+ ----------
114+ ats_percel: float, optional
115+ Fractional cell distance submitted by the ADV Package to the
116+ :class:`imod.mf6.AdaptiveTimeStepping` (ATS) package. If ``ats_percel``
117+ is specified and the ATS Package is active, a time step calculation will
118+ be made for each cell based on flow through the cell and cell
119+ properties. The largest time step will be calculated such that the
120+ advective fractional cell distance (``ats_percel``) is not exceeded for
121+ any active cell in the grid. This time-step constraint will be submitted
122+ to the ATS Package, perhaps with constraints submitted by other
123+ packages, in the calculation of the time step. ``ats_percel`` must be
124+ greater than zero. If a value of zero is specified for ``ats_percel``
125+ the program will automatically reset it to an internal no data value to
126+ indicate that time steps should not be subject to this constraint.
127+ Requires MODFLOW 6.6.0 or higher.
128+ validate: bool, optional
129+ Validate the package upon initialization. Defaults to True.
64130 """
65131
66- def __init__ (self , scheme : str = "central" ):
67- if not scheme == "central" :
68- raise ValueError (
69- "error in scheme parameter. Should be 'central' if present."
70- )
71- super ().__init__ (scheme = "central" )
132+ _scheme = "central"
72133
73134
74- class AdvectionTVD (Advection ):
135+ class AdvectionTVD (AdvectionBase ):
75136 """
76137 An implicit second order TVD scheme. More expensive than upstream
77138 weighting but more robust.
78- Note: all constructor arguments will be ignored
139+
140+ Parameters
141+ ----------
142+ ats_percel: float, optional
143+ Fractional cell distance submitted by the ADV Package to the
144+ :class:`imod.mf6.AdaptiveTimeStepping` (ATS) package. If ``ats_percel``
145+ is specified and the ATS Package is active, a time step calculation will
146+ be made for each cell based on flow through the cell and cell
147+ properties. The largest time step will be calculated such that the
148+ advective fractional cell distance (``ats_percel``) is not exceeded for
149+ any active cell in the grid. This time-step constraint will be submitted
150+ to the ATS Package, perhaps with constraints submitted by other
151+ packages, in the calculation of the time step. ``ats_percel`` must be
152+ greater than zero. If a value of zero is specified for ``ats_percel``
153+ the program will automatically reset it to an internal no data value to
154+ indicate that time steps should not be subject to this constraint.
155+ Requires MODFLOW 6.6.0 or higher.
156+ validate: bool, optional
157+ Validate the package upon initialization. Defaults to True.
79158 """
80159
81- def __init__ (self , scheme : str = "TVD" ):
82- if not scheme == "TVD" :
83- raise ValueError ("error in scheme parameter. Should be 'TVD' if present." )
84- super ().__init__ (scheme = "TVD" )
160+ _scheme = "TVD"
0 commit comments