MODFLOW 6  version 6.7.0.dev3
USGS Modular Hydrologic Model
VirtualModel.f90
Go to the documentation of this file.
4  use constantsmodule, only: lenmempath
5  use kindmodule, only: i4b, lgp
6  use listmodule, only: listtype
9  implicit none
10  private
11 
12  public :: cast_as_virtual_model
14  public :: get_virtual_model
15 
17  module procedure get_virtual_model_by_id, &
19  end interface
20 
21  type, public, extends(virtualdatacontainertype) :: virtualmodeltype
22  class(numericalmodeltype), pointer :: local_model
23  ! CON
24  type(virtualinttype), pointer :: con_ianglex => null()
25  type(virtualint1dtype), pointer :: con_ia => null()
26  type(virtualint1dtype), pointer :: con_ja => null()
27  type(virtualint1dtype), pointer :: con_jas => null()
28  type(virtualint1dtype), pointer :: con_ihc => null()
29  type(virtualdbl1dtype), pointer :: con_hwva => null()
30  type(virtualdbl1dtype), pointer :: con_cl1 => null()
31  type(virtualdbl1dtype), pointer :: con_cl2 => null()
32  type(virtualdbl1dtype), pointer :: con_anglex => null()
33  ! DIS
34  type(virtualinttype), pointer :: dis_ndim => null()
35  type(virtualinttype), pointer :: dis_nodes => null()
36  type(virtualinttype), pointer :: dis_nodesuser => null()
37  type(virtualint1dtype), pointer :: dis_nodeuser => null()
38  type(virtualinttype), pointer :: dis_nja => null()
39  type(virtualinttype), pointer :: dis_njas => null()
40  type(virtualdbltype), pointer :: dis_xorigin => null()
41  type(virtualdbltype), pointer :: dis_yorigin => null()
42  type(virtualdbltype), pointer :: dis_angrot => null()
43  type(virtualinttype), pointer :: dis_icondir => null()
44  type(virtualdbl1dtype), pointer :: dis_xc => null()
45  type(virtualdbl1dtype), pointer :: dis_yc => null()
46  type(virtualdbl1dtype), pointer :: dis_top => null()
47  type(virtualdbl1dtype), pointer :: dis_bot => null()
48  type(virtualdbl1dtype), pointer :: dis_area => null()
49  ! Numerical Model fields
50  type(virtualinttype), pointer :: moffset => null()
51  type(virtualdbl1dtype), pointer :: x => null()
52  type(virtualdbl1dtype), pointer :: x_old => null()
53  type(virtualint1dtype), pointer :: ibound => null()
54  ! Base Model fields
55  type(virtualinttype), pointer :: idsoln => null()
56  contains
57  ! public
58  procedure :: create => vm_create
59  procedure :: prepare_stage => vm_prepare_stage
60  procedure :: destroy => vm_destroy
61  generic :: operator(==) => eq_virtual_model, eq_numerical_model
62 
63  procedure :: dis_get_nodeuser
64  procedure :: dis_noder_to_string
65 
66  ! private
67  procedure, private :: init_virtual_data
68  procedure, private :: allocate_data
69  procedure, private :: deallocate_data
70  procedure, private :: eq_virtual_model
71  procedure, private :: eq_numerical_model
72  end type virtualmodeltype
73 
74 contains
75 
76  subroutine vm_create(this, name, id, model)
77  class(virtualmodeltype) :: this
78  character(len=*) :: name
79  integer(I4B) :: id
80  class(numericalmodeltype), pointer :: model
81  ! local
82  logical(LGP) :: is_local
83 
84  is_local = associated(model)
85  call this%VirtualDataContainerType%vdc_create(name, id, is_local)
86 
87  this%local_model => model
88 
89  call this%allocate_data()
90  call this%init_virtual_data()
91 
92  end subroutine vm_create
93 
94  subroutine init_virtual_data(this)
95  class(virtualmodeltype) :: this
96 
97  ! CON
98  call this%set(this%con_ianglex%base(), 'IANGLEX', 'CON', map_all_type)
99  call this%set(this%con_ia%base(), 'IA', 'CON', map_all_type)
100  call this%set(this%con_ja%base(), 'JA', 'CON', map_all_type)
101  call this%set(this%con_jas%base(), 'JAS', 'CON', map_all_type)
102  call this%set(this%con_ihc%base(), 'IHC', 'CON', map_all_type)
103  call this%set(this%con_hwva%base(), 'HWVA', 'CON', map_all_type)
104  call this%set(this%con_cl1%base(), 'CL1', 'CON', map_all_type)
105  call this%set(this%con_cl2%base(), 'CL2', 'CON', map_all_type)
106  call this%set(this%con_anglex%base(), 'ANGLEX', 'CON', map_all_type)
107  ! DIS
108  call this%set(this%dis_ndim%base(), 'NDIM', 'DIS', map_all_type)
109  call this%set(this%dis_nodes%base(), 'NODES', 'DIS', map_all_type)
110  call this%set(this%dis_nodesuser%base(), 'NODESUSER', 'DIS', map_all_type)
111  call this%set(this%dis_nodeuser%base(), 'NODEUSER', 'DIS', map_all_type)
112  call this%set(this%dis_nja%base(), 'NJA', 'DIS', map_all_type)
113  call this%set(this%dis_njas%base(), 'NJAS', 'DIS', map_all_type)
114  call this%set(this%dis_icondir%base(), 'ICONDIR', 'DIS', map_all_type)
115  call this%set(this%dis_xorigin%base(), 'XORIGIN', 'DIS', map_all_type)
116  call this%set(this%dis_yorigin%base(), 'YORIGIN', 'DIS', map_all_type)
117  call this%set(this%dis_angrot%base(), 'ANGROT', 'DIS', map_all_type)
118  call this%set(this%dis_xc%base(), 'XC', 'DIS', map_all_type)
119  call this%set(this%dis_yc%base(), 'YC', 'DIS', map_all_type)
120  call this%set(this%dis_top%base(), 'TOP', 'DIS', map_all_type)
121  call this%set(this%dis_bot%base(), 'BOT', 'DIS', map_all_type)
122  call this%set(this%dis_area%base(), 'AREA', 'DIS', map_all_type)
123  ! Numerical model
124  call this%set(this%moffset%base(), 'MOFFSET', '', map_all_type)
125  call this%set(this%x%base(), 'X', '', map_node_type)
126  call this%set(this%x_old%base(), 'XOLD', '', map_node_type)
127  call this%set(this%ibound%base(), 'IBOUND', '', map_node_type)
128  ! Base model
129  call this%set(this%idsoln%base(), 'IDSOLN', '', map_all_type)
130 
131  end subroutine init_virtual_data
132 
133  subroutine vm_prepare_stage(this, stage)
134  class(virtualmodeltype) :: this
135  integer(I4B) :: stage
136  ! local
137  integer(I4B) :: nodes, nodesuser, nja, njas, icondir
138  logical(LGP) :: is_reduced
139 
140  if (stage == stg_aft_mdl_df) then
141 
142  call this%map(this%idsoln%base(), (/stg_aft_mdl_df/))
143  call this%map(this%con_ianglex%base(), (/stg_aft_mdl_df/))
144  call this%map(this%dis_icondir%base(), (/stg_aft_mdl_df/))
145  call this%map(this%dis_ndim%base(), (/stg_aft_mdl_df/))
146  call this%map(this%dis_nodes%base(), (/stg_aft_mdl_df/))
147  call this%map(this%dis_nodesuser%base(), (/stg_aft_mdl_df/))
148  call this%map(this%dis_nja%base(), (/stg_aft_mdl_df/))
149  call this%map(this%dis_njas%base(), (/stg_aft_mdl_df/))
150 
151  else if (stage == stg_bfr_exg_ac) then
152 
153  nodes = this%dis_nodes%get()
154  nodesuser = this%dis_nodesuser%get()
155  is_reduced = (nodes /= nodesuser)
156  call this%map(this%moffset%base(), (/stg_bfr_exg_ac/))
157  if (is_reduced) then
158  call this%map(this%dis_nodeuser%base(), nodes, (/stg_bfr_exg_ac/))
159  else
160  ! no reduction, zero sized array, never synchronize
161  call this%map(this%dis_nodeuser%base(), 0, (/stg_never/))
162  end if
163 
164  else if (stage == stg_bfr_con_df) then
165 
166  nodes = this%dis_nodes%get()
167  nja = this%dis_nja%get()
168  njas = this%dis_njas%get()
169  icondir = this%dis_icondir%get()
170  ! DIS
171  call this%map(this%dis_xorigin%base(), (/stg_bfr_con_df/))
172  call this%map(this%dis_yorigin%base(), (/stg_bfr_con_df/))
173  call this%map(this%dis_angrot%base(), (/stg_bfr_con_df/))
174  if (icondir > 0) then
175  call this%map(this%dis_xc%base(), nodes, (/stg_bfr_con_df/))
176  call this%map(this%dis_yc%base(), nodes, (/stg_bfr_con_df/))
177  else
178  call this%map(this%dis_xc%base(), 0, (/stg_never/))
179  call this%map(this%dis_yc%base(), 0, (/stg_never/))
180  end if
181  call this%map(this%dis_top%base(), nodes, (/stg_bfr_con_df/))
182  call this%map(this%dis_bot%base(), nodes, (/stg_bfr_con_df/))
183  call this%map(this%dis_area%base(), nodes, (/stg_bfr_con_df/))
184  ! CON
185  call this%map(this%con_ia%base(), nodes + 1, (/stg_bfr_con_df/))
186  call this%map(this%con_ja%base(), nja, (/stg_bfr_con_df/))
187  call this%map(this%con_jas%base(), nja, (/stg_bfr_con_df/))
188  call this%map(this%con_ihc%base(), njas, (/stg_bfr_con_df/))
189  call this%map(this%con_hwva%base(), njas, (/stg_bfr_con_df/))
190  call this%map(this%con_cl1%base(), njas, (/stg_bfr_con_df/))
191  call this%map(this%con_cl2%base(), njas, (/stg_bfr_con_df/))
192  if (this%con_ianglex%get() > 0) then
193  call this%map(this%con_anglex%base(), njas, (/stg_bfr_con_df/))
194  else
195  call this%map(this%con_anglex%base(), 0, (/stg_never/))
196  end if
197 
198  end if
199 
200  end subroutine vm_prepare_stage
201 
202  !> @brief Get user node number from reduced number
203  !<
204  function dis_get_nodeuser(this, node_reduced) result(node_user)
205  class(virtualmodeltype) :: this !< this virtual model
206  integer(I4B), intent(in) :: node_reduced !< the reduced node number
207  integer(I4B) :: node_user !< the returned user node number
208 
209  if (this%dis_nodes%get() < this%dis_nodesuser%get()) then
210  node_user = this%dis_nodeuser%get(node_reduced)
211  else
212  node_user = node_reduced
213  end if
214 
215  end function dis_get_nodeuser
216 
217  subroutine dis_noder_to_string(this, node_reduced, node_str)
218  class(virtualmodeltype) :: this !< this virtual model
219  integer(I4B), intent(in) :: node_reduced !< reduced node number
220  character(len=*), intent(inout) :: node_str !< the string representative of the user node number
221  ! local
222  character(len=11) :: nr_str
223 
224  if (this%is_local) then
225  call this%local_model%dis%noder_to_string(node_reduced, node_str)
226  else
227  ! for now this will look like: (102r)
228  write (nr_str, '(i0)') node_reduced
229  node_str = '('//trim(adjustl(nr_str))//'r)'
230  end if
231 
232  end subroutine dis_noder_to_string
233 
234  subroutine vm_destroy(this)
235  class(virtualmodeltype) :: this
236 
237  call this%VirtualDataContainerType%destroy()
238  call this%deallocate_data()
239 
240  end subroutine vm_destroy
241 
242  subroutine allocate_data(this)
243  class(virtualmodeltype) :: this
244 
245  allocate (this%con_ianglex)
246  allocate (this%con_ia)
247  allocate (this%con_ja)
248  allocate (this%con_jas)
249  allocate (this%con_ihc)
250  allocate (this%con_hwva)
251  allocate (this%con_cl1)
252  allocate (this%con_cl2)
253  allocate (this%con_anglex)
254  allocate (this%dis_ndim)
255  allocate (this%dis_nodes)
256  allocate (this%dis_nodesuser)
257  allocate (this%dis_nodeuser)
258  allocate (this%dis_nja)
259  allocate (this%dis_njas)
260  allocate (this%dis_xorigin)
261  allocate (this%dis_yorigin)
262  allocate (this%dis_angrot)
263  allocate (this%dis_icondir)
264  allocate (this%dis_xc)
265  allocate (this%dis_yc)
266  allocate (this%dis_top)
267  allocate (this%dis_bot)
268  allocate (this%dis_area)
269  allocate (this%moffset)
270  allocate (this%x)
271  allocate (this%x_old)
272  allocate (this%ibound)
273  allocate (this%idsoln)
274 
275  end subroutine allocate_data
276 
277  subroutine deallocate_data(this)
278  class(virtualmodeltype) :: this
279 
280  ! CON
281  deallocate (this%con_ianglex)
282  deallocate (this%con_ia)
283  deallocate (this%con_ja)
284  deallocate (this%con_jas)
285  deallocate (this%con_ihc)
286  deallocate (this%con_hwva)
287  deallocate (this%con_cl1)
288  deallocate (this%con_cl2)
289  deallocate (this%con_anglex)
290  ! DIS
291  deallocate (this%dis_ndim)
292  deallocate (this%dis_nodes)
293  deallocate (this%dis_nodesuser)
294  deallocate (this%dis_nodeuser)
295  deallocate (this%dis_nja)
296  deallocate (this%dis_njas)
297  deallocate (this%dis_xorigin)
298  deallocate (this%dis_yorigin)
299  deallocate (this%dis_angrot)
300  deallocate (this%dis_icondir)
301  deallocate (this%dis_xc)
302  deallocate (this%dis_yc)
303  deallocate (this%dis_top)
304  deallocate (this%dis_bot)
305  deallocate (this%dis_area)
306  ! Numerical model
307  deallocate (this%moffset)
308  deallocate (this%x)
309  deallocate (this%x_old)
310  deallocate (this%ibound)
311  ! Base model
312  deallocate (this%idsoln)
313 
314  end subroutine deallocate_data
315 
316  function get_virtual_model_from_list(model_list, idx) result(v_model)
317  type(listtype) :: model_list
318  integer(I4B) :: idx
319  class(virtualmodeltype), pointer :: v_model
320  ! local
321  class(*), pointer :: obj_ptr
322 
323  obj_ptr => model_list%GetItem(idx)
324  v_model => cast_as_virtual_model(obj_ptr)
325  end function get_virtual_model_from_list
326 
327  function cast_as_virtual_model(obj_ptr) result(v_model)
328  class(*), pointer :: obj_ptr
329  class(virtualmodeltype), pointer :: v_model
330 
331  v_model => null()
332  select type (obj_ptr)
333  class is (virtualmodeltype)
334  v_model => obj_ptr
335  end select
336 
337  end function cast_as_virtual_model
338 
339  function eq_virtual_model(this, v_model) result(is_equal)
340  class(virtualmodeltype), intent(in) :: this
341  class(virtualmodeltype), intent(in) :: v_model
342  logical(LGP) :: is_equal
343 
344  is_equal = (this%id == v_model%id)
345 
346  end function eq_virtual_model
347 
348  function eq_numerical_model(this, num_model) result(is_equal)
349  class(virtualmodeltype), intent(in) :: this
350  class(numericalmodeltype), intent(in) :: num_model
351  logical(LGP) :: is_equal
352 
353  is_equal = (this%id == num_model%id)
354 
355  end function eq_numerical_model
356 
357  !> @brief Returns a virtual model with the specified id
358  !< from the global list, or null
359  function get_virtual_model_by_id(model_id) result(virtual_model)
361  integer(I4B) :: model_id
362  class(virtualmodeltype), pointer :: virtual_model
363  ! local
364  integer(I4B) :: i
365  class(*), pointer :: vm
366 
367  virtual_model => null()
368  do i = 1, virtual_model_list%Count()
369  vm => virtual_model_list%GetItem(i)
370  select type (vm)
371  class is (virtualmodeltype)
372  if (vm%id == model_id) then
373  virtual_model => vm
374  return
375  end if
376  end select
377  end do
378 
379  end function get_virtual_model_by_id
380 
381  !> @brief Returns a virtual model with the specified name
382  !< from the global list, or null
383  function get_virtual_model_by_name(model_name) result(virtual_model)
385  character(len=*) :: model_name
386  class(virtualmodeltype), pointer :: virtual_model
387  ! local
388  integer(I4B) :: i
389  class(*), pointer :: vm
390 
391  virtual_model => null()
392  do i = 1, virtual_model_list%Count()
393  vm => virtual_model_list%GetItem(i)
394  select type (vm)
395  class is (virtualmodeltype)
396  if (vm%name == model_name) then
397  virtual_model => vm
398  return
399  end if
400  end select
401  end do
402 
403  end function get_virtual_model_by_name
404 
405 end module virtualmodelmodule
This module contains simulation constants.
Definition: Constants.f90:9
integer(i4b), parameter lenmempath
maximum length of the memory path
Definition: Constants.f90:27
This module defines variable data types.
Definition: kind.f90:8
integer(i4b), parameter, public stg_aft_mdl_df
after model define
Definition: SimStages.f90:11
integer(i4b), parameter, public stg_never
never
Definition: SimStages.f90:9
integer(i4b), parameter, public stg_bfr_exg_ac
before exchange add connections (per solution)
Definition: SimStages.f90:16
integer(i4b), parameter, public stg_bfr_con_df
before connection define
Definition: SimStages.f90:14
integer(i4b), parameter, public map_all_type
Definition: VirtualBase.f90:13
integer(i4b), parameter, public map_node_type
Definition: VirtualBase.f90:14
type(listtype), public virtual_model_list
class(virtualmodeltype) function, pointer, public cast_as_virtual_model(obj_ptr)
logical(lgp) function eq_virtual_model(this, v_model)
subroutine vm_prepare_stage(this, stage)
subroutine vm_create(this, name, id, model)
integer(i4b) function dis_get_nodeuser(this, node_reduced)
Get user node number from reduced number.
class(virtualmodeltype) function, pointer get_virtual_model_by_id(model_id)
Returns a virtual model with the specified id.
subroutine deallocate_data(this)
subroutine init_virtual_data(this)
logical(lgp) function eq_numerical_model(this, num_model)
class(virtualmodeltype) function, pointer get_virtual_model_by_name(model_name)
Returns a virtual model with the specified name.
subroutine vm_destroy(this)
subroutine dis_noder_to_string(this, node_reduced, node_str)
subroutine allocate_data(this)
class(virtualmodeltype) function, pointer, public get_virtual_model_from_list(model_list, idx)
A generic heterogeneous doubly-linked list.
Definition: List.f90:14