1 ! This module is the base module for reservoirs that defines
2 ! abstract types for a reservoir base, reservoir state, and
3 ! reservoir properties. It also defines types for the inputs
4 ! and outputs common to all sub-types of reservoirs. Finally,
5 ! it defines a pointer to a reservoir object and an interface
6 ! for running a reservoir.
7 module module_reservoir
9 ! Defines the reservoir base state type that sub-types of
10 ! reservoirs will derive from. Since this is abstract, an instance
11 ! of reservoir state cannot be created but only derived to sub-types
12 ! of reservoirs. State holds and tracks dynamic/changing variables
13 ! that are only relevant to the given reservoir object and not other
14 ! modules or areas of the system.
15 type, abstract :: reservoir_state
19 ! Defines the reservoir base properties/parameters type that
20 ! sub-types of reservoirs will derive from. Since this is abstract,
21 ! an instance of reservoir properties cannot be created but only
22 ! derived to sub-types of reservoirs. Properties holds
23 ! static/unchanging variables that are set when the given reservoir
24 ! object is initialized/instantiated.
25 type, abstract :: reservoir_properties
29 ! Defines the input base type which holds the same inputs that all
30 ! sub-types of reservoirs will derive from. Therefore, all types of
31 ! reservoirs will hold the inputs defined below. These are
32 ! dynamic/changing variables that will receive values passed into the
33 ! object's methods/subroutines at runtime.
34 type :: reservoir_input
36 real :: inflow ! cubic meters per second (cms)
37 real :: lateral_inflow ! cubic meters per second (cms)
38 real :: previous_timestep_inflow ! cubic meters per second (cms)
42 procedure :: init => reservoir_input_init
43 procedure :: destroy => reservoir_input_destroy
47 ! Defines the output base type which holds the same output(s) that all
48 ! sub-types of reservoirs will derive from. Therefore, all types of
49 ! reservoirs will hold the output(s) defined below. These are
50 ! dynamic/changing variables that will receive values returned from the
51 ! object's methods/subroutines at runtime.
52 type :: reservoir_output
54 real :: outflow ! cubic meters per second (cms)
58 procedure :: init => reservoir_output_init
59 procedure :: destroy => reservoir_output_destroy
63 ! Defines the reservoir base type that sub-types of reservoirs
64 ! will derive from. Since this is abstract, an instance of reservoir
65 ! cannot be created but only derived to sub-types of reservoirs.
66 ! Derived sub-types of reservoirs of this base type will create a
67 ! reservoir object that will hold state, properties/parameters,
68 ! inputs, and outputs as sub-objects.
69 type, abstract :: reservoir
71 type(reservoir_input), pointer :: input
72 type(reservoir_output), pointer :: output
76 ! Defines procedure to call run reservoir for a type of reservoir,
77 ! which will then call methods/subroutines for processing the
78 ! inputs and returning the outputs. Since this is deferred,
79 ! it cannot be implemented for a base reservoir but only for
80 ! a sub-type of reservoir.
81 procedure (run_reservoir_interface), deferred :: run
85 ! Defines a pointer to a reservoir base type
86 type :: reservoir_container
87 class (reservoir), pointer :: ptr
90 ! Defines the abstract implementation of run_reservoir that all
91 ! reservoir sub-types will derive from with the same given
94 subroutine run_reservoir_interface(this, previous_timestep_inflow, inflow, &
95 lateral_inflow, water_elevation, outflow, routing_period, dynamic_reservoir_type, &
96 assimilated_value, assimilated_source_file)
98 class(reservoir), intent(inout) :: this
99 real, intent(in) :: previous_timestep_inflow ! cubic meters per second (cms)
100 real, intent(in) :: inflow ! cubic meters per second (cms)
101 real, intent(in) :: lateral_inflow ! cubic meters per second (cms)
102 real, intent(inout) :: water_elevation ! meters AMSL
103 real, intent(out) :: outflow ! cubic meters per second (cms)
104 real, intent(in) :: routing_period ! seconds
105 integer, intent(out):: dynamic_reservoir_type ! dynamic reservoir type sent to lake out files
106 real, intent(out) :: assimilated_value ! value assimilated from observation or forecast
107 character(len=256), intent(out) :: assimilated_source_file ! source file of assimilated value
109 end subroutine run_reservoir_interface
115 ! Constructor the reservoir input type
116 subroutine reservoir_input_init(this)
118 class (reservoir_input), intent(inout) :: this ! object being initialized
120 this%lateral_inflow = 0.0
121 this%previous_timestep_inflow = 0.0
123 end subroutine reservoir_input_init
126 ! Destructor for the reservoir input type
127 subroutine reservoir_input_destroy(this)
129 class (reservoir_input), intent(inout) :: this ! object being destroyed
131 end subroutine reservoir_input_destroy
134 ! Constructor for the reservoir output type
135 subroutine reservoir_output_init(this)
137 class (reservoir_output), intent(inout) :: this ! object being initialized
140 end subroutine reservoir_output_init
143 ! Destructor for the reservoir output type
144 subroutine reservoir_output_destroy(this)
146 class (reservoir_output), intent(inout) :: this ! object being destroyed
148 end subroutine reservoir_output_destroy
150 end module module_reservoir