LCOV - code coverage report
Current view: top level - mHM - mo_runoff.f90 (source / functions) Hit Total Coverage
Test: mHM coverage Lines: 23 27 85.2 %
Date: 2024-04-30 08:53:32 Functions: 3 3 100.0 %

          Line data    Source code
       1             : !> \file mo_runoff.f90
       2             : !> \brief \copybrief mo_runoff
       3             : !> \details \copydetails mo_runoff
       4             : 
       5             : !> \brief Runoff generation.
       6             : !> \details This module generates the runoff for the unsaturated and saturated zones and provides runoff accumulation.
       7             : !> \authors Vladyslav Prykhodko
       8             : !> \date Dec 2012
       9             : !> \copyright Copyright 2005-\today, the mHM Developers, Luis Samaniego, Sabine Attinger: All rights reserved.
      10             : !! mHM is released under the LGPLv3+ license \license_note
      11             : !> \ingroup f_mhm
      12             : MODULE mo_runoff
      13             : 
      14             :   USE mo_kind, ONLY : dp
      15             :   USE mo_common_constants, ONLY : eps_dp
      16             : 
      17             :   IMPLICIT NONE
      18             : 
      19             :   PUBLIC :: runoff_unsat_zone
      20             :   PUBLIC :: runoff_sat_zone
      21             :   PUBLIC :: L1_total_runoff
      22             : 
      23             :   PRIVATE
      24             : 
      25             :   ! ------------------------------------------------------------------
      26             : 
      27             : CONTAINS
      28             : 
      29             :   ! ------------------------------------------------------------------
      30             : 
      31             :   !    NAME
      32             :   !        runoff_unsat_zone
      33             : 
      34             :   !    PURPOSE
      35             :   !>       \brief Runoff generation for the saturated zone.
      36             : 
      37             :   !>       \details Calculates the runoff generation for the unsaturated zone.
      38             :   !>       Calculates percolation, interflow and baseflow.
      39             :   !>       Updates upper soil and groundwater storages.
      40             : 
      41             :   !    INTENT(IN)
      42             :   !>       \param[in] "REAL(dp) :: k1"           Recession coefficient of the upper reservoir,lower outlet [TS-1]
      43             :   !>       \param[in] "REAL(dp) :: kp"           Percolation coefficient [TS-1]
      44             :   !>       \param[in] "REAL(dp) :: k0"           Recession coefficient of the upperreservoir, upper outlet [TS-1]
      45             :   !>       \param[in] "REAL(dp) :: alpha"        Exponent for the upper reservoir [-]
      46             :   !>       \param[in] "REAL(dp) :: karst_loss"   Karstic percolation loss [-]
      47             :   !>       \param[in] "REAL(dp) :: pefec_soil"   Input to the soil layer [mm]
      48             :   !>       \param[in] "REAL(dp) :: unsat_thresh" Threshold water depth in upper reservoir(for Runoff contribution) [mm]
      49             : 
      50             :   !    INTENT(INOUT)
      51             :   !>       \param[inout] "REAL(dp) :: sat_storage"   Groundwater storage [mm]
      52             :   !>       \param[inout] "REAL(dp) :: unsat_storage" Upper soil storage [mm]
      53             : 
      54             :   !    INTENT(OUT)
      55             :   !>       \param[out] "REAL(dp) :: slow_interflow" Slow runoff component [mm TS-1]
      56             :   !>       \param[out] "REAL(dp) :: fast_interflow" Fast runoff component [mm TS-1]
      57             :   !>       \param[out] "REAL(dp) :: perc"           Percolation [mm TS-1]
      58             : 
      59             :   !    HISTORY
      60             :   !>       \authors Vladyslav Prykhodko
      61             : 
      62             :   !>       \date Dec 2012
      63             : 
      64             :   ! Modifications:
      65             :   ! LS Feb 2006 - fast response
      66             :   ! LS Feb 2007 - MaxInter
      67             :   ! RK May 2007 - fracArea, errors in Qmod
      68             :   ! LS Dec 2012 - variable names and process sat. zone
      69             :   ! LS Jan 2013 - total runoff accumulation L11
      70             :   ! JM Aug 2013 - ordering of arguments changed
      71             :   ! Robert Schweppe Jun 2018 - refactoring and reformatting
      72             : 
      73             : 
      74    76647048 :   SUBROUTINE runoff_unsat_zone(k1, kp, k0, alpha, karst_loss, pefec_soil, unsat_thresh, sat_storage, unsat_storage, &
      75             :                               slow_interflow, fast_interflow, perc)
      76             :     implicit none
      77             : 
      78             :     ! Recession coefficient of the upper reservoir,lower outlet [TS-1]
      79             :     REAL(dp), INTENT(IN) :: k1
      80             : 
      81             :     ! Percolation coefficient [TS-1]
      82             :     REAL(dp), INTENT(IN) :: kp
      83             : 
      84             :     ! Recession coefficient of the upperreservoir, upper outlet [TS-1]
      85             :     REAL(dp), INTENT(IN) :: k0
      86             : 
      87             :     ! Exponent for the upper reservoir [-]
      88             :     REAL(dp), INTENT(IN) :: alpha
      89             : 
      90             :     ! Karstic percolation loss [-]
      91             :     REAL(dp), INTENT(IN) :: karst_loss
      92             : 
      93             :     ! Input to the soil layer [mm]
      94             :     REAL(dp), INTENT(IN) :: pefec_soil
      95             : 
      96             :     ! Threshold water depth in upper reservoir(for Runoff contribution) [mm]
      97             :     REAL(dp), INTENT(IN) :: unsat_thresh
      98             : 
      99             :     ! Groundwater storage [mm]
     100             :     REAL(dp), INTENT(INOUT) :: sat_storage
     101             : 
     102             :     ! Upper soil storage [mm]
     103             :     REAL(dp), INTENT(INOUT) :: unsat_storage
     104             : 
     105             :     ! Slow runoff component [mm TS-1]
     106             :     REAL(dp), INTENT(OUT) :: slow_interflow
     107             : 
     108             :     ! Fast runoff component [mm TS-1]
     109             :     REAL(dp), INTENT(OUT) :: fast_interflow
     110             : 
     111             :     ! Percolation [mm TS-1]
     112             :     REAL(dp), INTENT(OUT) :: perc
     113             : 
     114             : 
     115             :     !---------------------------------------------------------------
     116             :     ! SOIL LAYER BETWEEN UNSATURATED AND SATURATED ZONE
     117             :     !---------------------------------------------------------------
     118             :     ! HERE input is from last soil Horizon...
     119             :     !pefec_soil = Cell1_soil(k, nHorizons_mHM)%infil
     120    76647048 :     unsat_storage = unsat_storage + pefec_soil
     121             : 
     122             :     ! FAST INTERFLOW WITH THRESHOLD BEHAVIOUR
     123    76647048 :     fast_interflow = 0.0_dp
     124    76647048 :     if(unsat_storage > unsat_thresh) then
     125             :       fast_interflow = MIN((k0 * (unsat_storage - unsat_thresh)), &
     126     5975469 :               (unsat_storage - eps_dp))
     127             :     end if
     128    76647048 :     unsat_storage = unsat_storage - fast_interflow
     129             : 
     130             :     ! SLOW PERMANENT INTERFLOW
     131    76647048 :     slow_interflow = 0.0_dp
     132             : 
     133    76647048 :     if(unsat_storage > eps_dp) then
     134             :       slow_interflow = min((k1 * (unsat_storage**(1.0_dp + alpha))), &
     135    76647048 :               (unsat_storage - eps_dp))
     136             :     end if
     137    76647048 :     unsat_storage = unsat_storage - slow_interflow
     138             : 
     139             :     !--------------------------------------------------------
     140             :     ! PERCOLATION FROM SOIL LAYER TO THE SATURATED ZONE
     141             :     !--------------------------------------------------------
     142    76647048 :     perc = kp * unsat_storage
     143             : 
     144             :     ! Taking into account for the KARSTIC aquifers
     145             :     !*** karstic loss gain or loss if Karstic aquifer is present...
     146    76647048 :     if(unsat_storage > perc) then
     147    76647048 :       unsat_storage = unsat_storage - perc
     148    76647048 :       sat_storage = sat_storage + perc * karst_loss
     149             :     else
     150           0 :       sat_storage = sat_storage + unsat_storage * karst_loss
     151           0 :       unsat_storage = 0.0_dp
     152             :     end if
     153             : 
     154    76647048 :   END SUBROUTINE runoff_unsat_zone
     155             : 
     156             :   ! ------------------------------------------------------------------
     157             : 
     158             :   !    NAME
     159             :   !        runoff_sat_zone
     160             : 
     161             :   !    PURPOSE
     162             :   !>       \brief Runoff generation for the saturated zone.
     163             : 
     164             :   !>       \details Calculates the runoff generation for the saturated zone.
     165             :   !>       If the level of the ground water reservoir is zero, then
     166             :   !>       the baseflow is also zero.
     167             :   !>       If the level of the ground water reservoir is greater than zero, then
     168             :   !>       the baseflow is equal to baseflow recession coefficient times the level
     169             :   !>       of the ground water reservoir, which
     170             :   !>       will be then reduced by the value of baseflow.
     171             : 
     172             :   !    INTENT(IN)
     173             :   !>       \param[in] "REAL(dp) :: k2" Baseflow recession coefficient [TS-1]
     174             : 
     175             :   !    INTENT(INOUT)
     176             :   !>       \param[inout] "REAL(dp) :: sat_storage" Groundwater storage [mm]
     177             : 
     178             :   !    INTENT(OUT)
     179             :   !>       \param[out] "REAL(dp) :: baseflow" Baseflow [mm TS-1]
     180             : 
     181             :   !    HISTORY
     182             :   !>       \authors Vladyslav Prykhodko
     183             : 
     184             :   !>       \date Dec 2012
     185             : 
     186             :   ! Modifications:
     187             :   ! JM Aug 2013 - ordering of arguments changed
     188             :   ! Robert Schweppe Jun 2018 - refactoring and reformatting
     189             : 
     190             : 
     191    76647048 :   SUBROUTINE runoff_sat_zone(k2, sat_storage, baseflow)
     192             :     implicit none
     193             : 
     194             :     ! Baseflow recession coefficient [TS-1]
     195             :     REAL(dp), INTENT(IN) :: k2
     196             : 
     197             :     ! Groundwater storage [mm]
     198             :     REAL(dp), INTENT(INOUT) :: sat_storage
     199             : 
     200             :     ! Baseflow [mm TS-1]
     201             :     REAL(dp), INTENT(OUT) :: baseflow
     202             : 
     203             : 
     204    76647048 :     if (sat_storage > 0.0_dp) then
     205    76647048 :       baseflow = k2 * sat_storage
     206    76647048 :       sat_storage = sat_storage - baseflow
     207             :     else
     208           0 :       baseflow = 0.0_dp
     209           0 :       sat_storage = 0.0_dp
     210             :     end if
     211             : 
     212    76647048 :   END SUBROUTINE runoff_sat_zone
     213             : 
     214             : 
     215             :   ! ------------------------------------------------------------------
     216             : 
     217             :   !    NAME
     218             :   !        L1_total_runoff
     219             : 
     220             :   !    PURPOSE
     221             :   !>       \brief total runoff accumulation at level 1
     222             : 
     223             :   !>       \details Accumulates runoff.
     224             :   !>       \f[ q_{T} = ( q_0 + q_1 + q_2 ) * (1-fSealed) + q_{D} * fSealed \f],
     225             :   !>       where fSealed is the fraction of sealed area.
     226             : 
     227             :   !    INTENT(IN)
     228             :   !>       \param[in] "REAL(dp) :: fSealed_area_fraction" sealed area fraction [1]
     229             :   !>       \param[in] "REAL(dp) :: fast_interflow"        \f$ q_0 \f$ Fast runoff component [mm TS-1]
     230             :   !>       \param[in] "REAL(dp) :: slow_interflow"        \f$ q_1 \f$ Slow runoff component [mm TS-1]
     231             :   !>       \param[in] "REAL(dp) :: baseflow"              \f$ q_2 \f$ Baseflow [mm TS-1]
     232             :   !>       \param[in] "REAL(dp) :: direct_runoff"         \f$ q_D \f$ Direct runoff from impervious areas  [mm TS-1]
     233             : 
     234             :   !    INTENT(OUT)
     235             :   !>       \param[out] "REAL(dp) :: total_runoff" \f$ q_T \f$ Generated runoff [mm TS-1]
     236             : 
     237             :   !    HISTORY
     238             :   !>       \authors Vladyslav Prykhodko
     239             : 
     240             :   !>       \date Dec 2012
     241             : 
     242             :   ! Modifications:
     243             :   ! RK Jul 2013 - A Mosiac approach is implemented for processes accounted within the permeamble & impervious area.
     244             :   ! ST May 2015 - updated equation in the documentation
     245             :   ! Robert Schweppe Jun 2018 - refactoring and reformatting
     246             : 
     247             : 
     248    76647048 :   SUBROUTINE L1_total_runoff(fSealed_area_fraction, fast_interflow, slow_interflow, baseflow, direct_runoff, &
     249             :                             total_runoff)
     250             :     implicit none
     251             : 
     252             :     ! sealed area fraction [1]
     253             :     REAL(dp), INTENT(IN) :: fSealed_area_fraction
     254             : 
     255             :     ! \f$ q_0 \f$ Fast runoff component [mm TS-1]
     256             :     REAL(dp), INTENT(IN) :: fast_interflow
     257             : 
     258             :     ! \f$ q_1 \f$ Slow runoff component [mm TS-1]
     259             :     REAL(dp), INTENT(IN) :: slow_interflow
     260             : 
     261             :     ! \f$ q_2 \f$ Baseflow [mm TS-1]
     262             :     REAL(dp), INTENT(IN) :: baseflow
     263             : 
     264             :     ! \f$ q_D \f$ Direct runoff from impervious areas  [mm TS-1]
     265             :     REAL(dp), INTENT(IN) :: direct_runoff
     266             : 
     267             :     ! \f$ q_T \f$ Generated runoff [mm TS-1]
     268             :     REAL(dp), INTENT(OUT) :: total_runoff
     269             : 
     270             : 
     271             :     total_runoff = ((baseflow + slow_interflow + fast_interflow) * (1.0_dp - fSealed_area_fraction)) + &
     272    76647048 :             (direct_runoff * fSealed_area_fraction)
     273             : 
     274    76647048 :   END SUBROUTINE L1_total_runoff
     275             : 
     276             : END MODULE mo_runoff

Generated by: LCOV version 1.16