Skip to content

Commit a92d2dc

Browse files
committed
relevant for UHG-routing:
FIX: for certain parameter constellations, the UHG was not computed correctly and could result in negative routing coefficients / storages. Probably not significant for most constellations. Clarified computation of UHG
1 parent 2d070fb commit a92d2dc

File tree

1 file changed

+50
-69
lines changed

1 file changed

+50
-69
lines changed

src/River/routing.f90

Lines changed: 50 additions & 69 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ SUBROUTINE routing(STATUS)
2323
INTEGER :: irout,idummy,id !,imun,imunx,irout2,irout_d,imeso,istate
2424
INTEGER :: upstream, downstream
2525
INTEGER :: itl, ih, i, j, istate, h !, mm, imunout, iout, make
26-
REAL :: temp2, temp3, temp4, qtemp, x, b, y, hi !,xdum(48),storcapact
26+
REAL :: temp2, temp3, temp4, qtemp !, x, b, y, hi !,xdum(48),storcapact
2727
character(len=1000) :: fmtstr !string for formatting file output
2828

2929

@@ -129,74 +129,55 @@ SUBROUTINE routing(STATUS)
129129
hrout_intern=0.
130130

131131
DO i=1,subasin
132-
!compute values of triangular function at full integer points (0.5 is added because we assume the pulse to be routed centered at mid-day)
133-
itl = ceiling (prout(i,1)) !index to position in which peak will be located
134-
j = ceiling (prout(i,1)+prout(i,2) ) ! (integer index to end of triangle)
135-
136-
!internal response function (hrout_intern)
137-
!1. compute y-values of triangular function AT full integer points (ih=1 denotes t=0)
138-
if (prout(i,1) > 0) then
139-
DO ih = 1, floor(prout(i,1))+1 !rising limb
140-
hrout_intern(ih,i) = (ih-1)*1/prout(i,1)
141-
END DO
142-
end if
143-
144-
temp2=hrout_intern(itl,i) !keep first and last valid value of triangle - they'll be overwritten in the next steps
145-
temp3=hrout_intern(itl+1,i)
146-
147-
! considering that the value of response function changes within the time step, we want its mean:
148-
!2. compute MEAN values of triangular function BETWEEN full integer points
149-
DO ih = 1,(itl-1)
150-
hrout_intern(ih,i) = ( hrout_intern(ih,i) + hrout_intern(ih+1,i)) / 2
151-
END DO
152-
temp4 = 1- (itl - (0.5 + prout(i,1))) !fraction of rising limb in interval of peak
153-
hrout_intern(itl,i) = ( (temp2 + 1) * temp4 +&
154-
(temp3 + 1) * (1-temp4 ) ) / 2
155-
156-
157-
!external response function (hrout)
158-
if (itl > j) then !triangle fits completely into single interval
159-
hrout(itl,i)=1.
160-
else
161-
!compute y-values of triangular function AT full integer points (ih=1 denotes t=1)
162-
DO ih = itl, j+1
163-
hrout(ih,i) = 1. - (ih - (prout(i,1)+1))/prout(i,2)
164-
END DO
165-
166-
temp2=hrout(itl,i) !keep first and last valid value of triangle - they'll be overwritten in the next steps
167-
temp3=hrout(j,i)
168-
! considering that the value of response function changes within the time step, we want its mean:
169-
170-
!interval containing start of triangle, only covered by a fraction
171-
!do some geometry:
172-
if (itl /= ceiling(prout(i,1))) then !not necessary, if tlag is integer
173-
x = min(itl - prout(i,1), prout(i,2))
174-
b = hrout(itl+1,i)
175-
!A1 = x*b
176-
y = prout(i,1) - floor(prout(i,1))
177-
hi = (temp2 - b) * x / (x+y)
178-
!A2 = x*hi/2
179-
!hrout(itl,i) = (A1+A2) / x
180-
hrout(itl,i) = (b+hi/2)
181-
end if
182-
183-
!compute MEAN values of traingular function BETWEEN full integer points (function BETWEEN full integer points (complete intervals only)
184-
DO ih = itl+1,j
185-
hrout(ih,i) = ( hrout(ih+1,i) + hrout(ih,i)) / 2
186-
END DO
187-
188-
!interval containing end of triangle, only covered by a fraction (if any)
189-
hrout(j+1,i) = temp3/2 * (max(0.,prout(i,1)+prout(i,2) - j))
190-
end if
191-
hrout(:,i) = hrout(:,i) / sum(hrout(:,i)) !normalize response function
192-
hrout_intern(:,i) = hrout_intern(:,i) / sum(hrout_intern(:,i)) !normalize response function
193-
194-
temp2= prout(i,1) / (prout(i,1)+prout(i,2)) ! fraction of rising limb in hrout_internal
195-
hrout_intern(:,i) = temp2*hrout_intern(:,i) + (1-temp2) * hrout(:,i) !the falling limbs of the hydrographs should be identical
196-
197-
hrout_intern(:,i) = hrout_intern(:,i) / sum(hrout_intern(:,i)) !normalize just for safety, shouldnt be necessary
198-
199-
if (sum(hrout(:,i))==0 .OR. sum(hrout_intern(:,i))==0) then
132+
itl = ceiling (prout(i,1)) !index to position in hrout where peak will be located
133+
j = ceiling ( prout(i,1)+prout(i,2) ) ! (integer index to end of triangle)
134+
135+
if(itl > 1) then
136+
do ih = 1,(itl-1) !ascending part
137+
hrout_intern(ih,i) = (ih-0.5) / prout(i,1)
138+
hrout (ih,i) = 0
139+
end do
140+
temp2 = hrout_intern(itl-1,i)
141+
end if
142+
143+
!peak interval
144+
145+
temp2 = (itl-1) / prout(i,1) !value AT interval border before itl
146+
temp4 = 1 -(itl - prout(i,1)) !fraction of rising limb in interval of peak !!r
147+
148+
hrout_intern(itl,i) = (temp2 + 1)/2 * temp4
149+
150+
temp3 = 1- temp4 - max(0., (itl - (prout(i,1) + prout(i,2)))) !fraction of falling limb in interval of peak
151+
152+
temp2 = 1 - temp3 / prout(i,2) !value AT interval border after itl (or end of triangle)
153+
154+
hrout (itl,i) = (1 + temp2)/2 * temp3
155+
hrout_intern(itl,i) = hrout_intern(itl,i) + hrout (itl,i)
156+
157+
!recession part - do fully covered intervals only
158+
if (itl+1 < prout(i,1) + prout(i,2)) then
159+
do ih = (itl+1),(j-1) !recession part
160+
temp4 = 1 - (ih-0.5-prout(i,1)) / prout(i,2)
161+
hrout_intern(ih,i) = temp4 !recession parts of internal and external UHG are identical
162+
hrout (ih,i) = temp4
163+
end do
164+
end if
165+
166+
!remaining part of triangle that ends midway in interval
167+
temp4 = j - (prout(i,1) + prout(i,2)) !fraction of interval covered by triangle tail
168+
if (temp4 == 0) temp4=1 !special case: triangle ends exactly at interval border
169+
170+
temp2 = 1 - (j-1-prout(i,1)) / prout(i,2) !value AT interval border before j
171+
172+
temp3 = (temp2 + 0)/2 * temp4
173+
hrout_intern(j,i) = temp3 !recession parts of internal and external UHG are identical
174+
hrout (j,i) = temp3
175+
176+
hrout(:,i) = hrout(:,i) / sum(hrout(:,i)) !normalize response function
177+
hrout_intern(:,i) = hrout_intern(:,i) / sum(hrout_intern(:,i)) !normalize response function
178+
179+
180+
if (sum(hrout(:,i))==0 .OR. sum(hrout_intern(:,i))==0 .OR. any(hrout<0) .OR. any(hrout_intern<0)) then
200181
write(*,*) "Error when computing response functions: Please send response.dat to the developers."
201182
stop
202183
end if

0 commit comments

Comments
 (0)