lstream_v002

Version 2 of HydPy-L-Stream is a computationally more efficient alternative to application model lstream_v001. The higher efficiency is due to not calculating discharges based on channel geometries but preprocessed relationships between velocity and storage, similar to the “V/Q-BEZIEHUNG EXTERN” option of LARSIM.

The “parameter” VG2FG describes this relationship. You can configure it to either use a piecewise linear, a spline, or a neural network-based interpolation technique. See modules anntools and ppolytools for further information. Principally, VG2FG can fit any relationship provided by lstream_v001 very accurately. However, high accuracy might require a considerable number of polynomials or neurons. At least the latter can come with a relevant performance cost.

For simple use cases, one can assign a single value to parameter VG2FG, either a constant flow velocity or a constant delay time. lstream_v002 then works like the often-applied linear storage cascade.

Integration tests

Note

When new to HydPy, consider reading section How to understand integration tests? first.

main channel flow

The following integration test repeats the main channel flow example of the documentation on application model lstream_v001. The spatial and temporal settings are identical:

>>> from hydpy import ANN, pub, Nodes, Element
>>> pub.timegrids = "2000-01-01", "2000-01-05", "30m"
>>> from hydpy.models.lstream_v002 import *
>>> parameterstep("30m")
>>> nodes = Nodes("input1", "input2", "output")
>>> stream = Element("stream",
...                  inlets=["input1", "input2"],
...                  outlets="output")
>>> stream.model = model

We again divide a channel of 100 km length into eight subsections:

>>> laen(100.0)
>>> gts(8)
>>> ek(1.0)

Next, we define a relatively small neural network consisting of three neurons in a single hidden layer. This network roughly approximates the flow velocity calculated by the Gauckler-Manning-Strickler equation on the triple trapezoid profile defined in the main channel flow example:

>>> vg2fg(ANN(nmb_neurons=(3,),
...           weights_input=[[1.239962, 8.434961, 0.116195]],
...           weights_output=[[28.031913],
...                           [22.114402],
...                           [85.802384]],
...           intercepts_hidden=[[4.346762, 4.553889, 4.197525]],
...           intercepts_output=[-134.031566]))

In contrast to application model lstream_v001, lstream_v002 uses the stored water volume (VG) as its state variable instead of the water stage (H). Hence, we now must set VG to a value resulting in an initial outflow of 100 m³/s for the defined parameterisation of VG2FG, which holds for 1.55884384 million m³:

>>> from hydpy.core.testtools import IntegrationTest
>>> IntegrationTest.plotting_options.activated = fluxes.qz, fluxes.qa
>>> test = IntegrationTest(stream, inits=[[states.vg, 1.55884384]])

Finally, we define two identical inflow time series:

>>> import numpy
>>> q_base = 100.0
>>> q_peak = 900.0
>>> t_peak = 24.0
>>> β = 16.0
>>> ts = pub.timegrids.init.to_timepoints()
>>> nodes.input1.sequences.sim.series = q_base
>>> nodes.input2.sequences.sim.series = (
...     (q_peak-q_base)*((ts/t_peak)*numpy.exp(1.0-ts/t_peak))**β)

Our approximation of the velocity-storage relationship is far from perfect. Still, it is, at least in the range relevant for the selected event, sufficient to reproduce the original results of application model lstream_v001 with reasonable accuracy (for example, peak flow is 659.6 m³/s instead of 659.0 m³/s):

>>> test("lstream_v002_main_channel_flow")
Click to see the table
Click to see the graph

linear storage cascade

This example shows how to use lstream_v002 like a simple linear storage cascade. Therefore, you need to assign a constant flow velocity to parameter VG2FG via the keyword argument velocity in m/s. Alternatively, you can define the number of hours it takes for a flood wave to travel through the whole channel via the keyword argument timedelay.

When defining a constant flow velocity, be aware that this is also the wave celerity due to the assumed linearity. Hence, we set a velocity of 1.5 m/s, which is higher than the average flow velocity in the main channel flow example but leads to comparable results.

Note that, even when used as a linear storage cascade, lstream_v002 still relies on the numerical integration of its set of differential equations. Hence, it is computationally less efficient than Unit Hydrograph based approaches like those implemented in application model arma_v1, especially for short channels and high numbers of channel subsections. On the other hand, lstream_v002 only requires the actual water volume stored in the subsections for describing its current state, which is more concise and understandable than the logged values of arma_v1 and can simplify the coupling with data assimilation approaches.

>>> vg2fg(velocity=1.5)
>>> test.inits.vg = 0.83333333
>>> test("lstream_v002_linear_storage_cascade")
Click to see the table
Click to see the graph

directly forwarded runoff

If you need to forward the runoff directly (as if the channel length would be zero), set the number of subchannels to zero:

>>> laen(0.0)
>>> gts(0)
>>> test("lstream_v002_directly_forwarded_runoff")
Click to see the table
Click to see the graph
class hydpy.models.lstream_v002.Model[source]

Bases: Model

Version 2 of HydPy-L-Stream.

The following “inlet update methods” are called in the given sequence at the beginning of each simulation step:
  • Pick_Q_V1 Query the current inflow from all inlet nodes.

The following methods define the relevant components of a system of ODE equations (e.g. direct runoff):
  • Calc_QZA_V1 Calculate the current inflow into the channel.

  • Calc_QG_V2 Calculate the discharge of the total cross-section based on an interpolated flow velocity.

  • Calc_QA_V1 Query the actual outflow.

The following methods define the complete equations of an ODE system (e.g. change in storage of fast water due to effective precipitation and direct runoff):
The following “outlet update methods” are called in the given sequence at the end of each simulation step:
  • Pass_Q_V1 Pass the outflow to the outlet node.

class hydpy.models.lstream_v002.ControlParameters(master: Parameters, cls_fastaccess: Type[FastAccessParameter] | None = None, cymodel: CyModelProtocol | None = None)

Bases: SubParameters

Control parameters of model lstream_v002.

The following classes are selected:
  • Laen() Flusslänge (channel length) [km].

  • GTS() Anzahl Gewässerteilstrecken (number of channel subsections) [-].

  • VG2FG() Flexibler Interpolator zur Berechnung der Fließgeschwindigkeit in Abhängigkeit zur aktuellen Wasserspeicherung einer Gewässerteilstrecke (flexible interpolator describing the relationship between the flow velocity and the water storage of individual channel subsections) [m/s].

  • EK() Kalibrierfaktor (calibration factor) [-].

class hydpy.models.lstream_v002.DerivedParameters(master: Parameters, cls_fastaccess: Type[FastAccessParameter] | None = None, cymodel: CyModelProtocol | None = None)

Bases: SubParameters

Derived parameters of model lstream_v002.

The following classes are selected:
  • Sek() Sekunden im Simulationszeitschritt (Number of seconds of the selected simulation time step) [s].

class hydpy.models.lstream_v002.FluxSequences(master: Sequences, cls_fastaccess: Type[TypeFastAccess_co] | None = None, cymodel: CyModelProtocol | None = None)

Bases: FluxSequences

Flux sequences of model lstream_v002.

The following classes are selected:
  • QZ() Mittlerer Zufluss in Gerinnestrecke (average inflow into the channel) [m³/s].

  • QZA() Aktueller Zufluss in Gerinnestrecke (current inflow into the channel) [m³/s].

  • QG() Durchfluss gesamt (total discharge) [m³/s].

  • QA() Abfluss aus Gerinnestrecke (outflow out of the channel) [m³/s].

class hydpy.models.lstream_v002.InletSequences(master: Sequences, cls_fastaccess: Type[TypeFastAccess_co] | None = None, cymodel: CyModelProtocol | None = None)

Bases: InletSequences

Inlet sequences of model lstream_v002.

The following classes are selected:
  • Q() Abfluss (runoff) [m³/s].

class hydpy.models.lstream_v002.OutletSequences(master: Sequences, cls_fastaccess: Type[TypeFastAccess_co] | None = None, cymodel: CyModelProtocol | None = None)

Bases: OutletSequences

Outlet sequences of model lstream_v002.

The following classes are selected:
  • Q() Abfluss (runoff) [m³/s].

class hydpy.models.lstream_v002.SolverParameters(master: Parameters, cls_fastaccess: Type[FastAccessParameter] | None = None, cymodel: CyModelProtocol | None = None)

Bases: SubParameters

Solver parameters of model lstream_v002.

The following classes are selected:
  • AbsErrorMax() Absolute numerical error tolerance [m3/s].

  • RelErrorMax() Relative numerical error tolerance [-].

  • RelDTMin() Smallest relative integration time step size allowed [-].

  • RelDTMax() Largest relative integration time step size allowed [-].

class hydpy.models.lstream_v002.StateSequences(master: Sequences, cls_fastaccess: Type[TypeFastAccess_co] | None = None, cymodel: CyModelProtocol | None = None)

Bases: StateSequences

State sequences of model lstream_v002.

The following classes are selected:
  • VG() Wasservolumen (water volume) [million m³].