SURFEX  V8_0
Surfex V8_0 release
 All Classes Files Functions Variables
z0eff.F90
Go to the documentation of this file.
1 !SFX_LIC Copyright 1994-2014 CNRS, Meteo-France and Universite Paul Sabatier
2 !SFX_LIC This is part of the SURFEX software governed by the CeCILL-C licence
3 !SFX_LIC version 1. See LICENSE, CeCILL-C_V1-en.txt and CeCILL-C_V1-fr.txt
4 !SFX_LIC for details. version 1.
5 ! #########
6  SUBROUTINE z0eff (I, &
7  hrough, omeb, palfa, pzref, puref, pz0, pz0rel, ppsn, &
8  ppalphan,pz0litter, pwsnow, &
9  pz0effip,pz0effim,pz0effjp,pz0effjm,pff,pz0_flood, &
10  paosip,paosim,paosjp,paosjm,pho2ip,pho2im,pho2jp,pho2jm, &
11  pz0_o_z0h, pz0_with_snow, pz0h_with_snow,pz0eff, &
12  pz0g_without_snow, &
13  pz0_mebv,pz0h_mebv,pz0eff_mebv, &
14  pz0_mebn,pz0h_mebn,pz0eff_mebn )
15 
16 ! ############################################################################
17 !
18 !!**** *Z0EFF*
19 !!
20 !! PURPOSE
21 !! -------
22 !
23 ! Calculates the z0eff for momentum fluxes according to wind direction.
24 !
25 !
26 !!** METHOD
27 !! ------
28 !
29 !
30 !! EXTERNAL
31 !! --------
32 !!
33 !!
34 !! IMPLICIT ARGUMENTS
35 !! ------------------
36 !!
37 !!
38 !! REFERENCE
39 !! ---------
40 !!
41 !! Mascart et al. (1995)
42 !! Belair (1995)
43 !!
44 !! AUTHOR
45 !! ------
46 !!
47 !! S. Belair * Meteo-France *
48 !!
49 !! MODIFICATIONS
50 !! -------------
51 !! Original 13/03/95
52 !! (J.Stein) 15/11/95 use the potential temperature to compute Ri
53 !! and PVMOD instead of ZVMOD
54 !! (P.Lacarrere)15/03/96 replace * PEXNS by / PEXNS
55 !! (V.Masson) 22/12/97 computation of z0eff after snow treatment
56 !! (V.Masson) 05/10/98 clear routine
57 !! (A.Boone) 11/26/98 Option for PDELTA: forested vs default surface
58 !! (V Masson) 12/07/01 new formulation for aggregation with snow z0
59 !! (P.LeMoigne) 09/02/06 computation of z0h in presence of snow
60 !! (B. Decharme) 2008 floodplains
61 !! (P. Samuelsson) 10/2014 MEB
62 !! P. LeMoigne 12/2014 EBA scheme update
63 !-------------------------------------------------------------------------------
64 !
65 !* 0. DECLARATIONS
66 ! ------------
67 !
68 !
69 USE modd_isba_n, ONLY : isba_t
70 !
71 USE modd_csts, ONLY : xpi, xg
72 USE modd_snow_par, ONLY : xz0sn, xwcrn, xz0hsn
73 !
75 USE modd_surf_atm, ONLY : laldz0h
76 !
77 !
78 USE yomhook ,ONLY : lhook, dr_hook
79 USE parkind1 ,ONLY : jprb
80 !
81 IMPLICIT NONE
82 !
83 !* 0.1 declarations of arguments
84 !
85 !
86 !
87 TYPE(isba_t), INTENT(INOUT) :: i
88 !
89  CHARACTER(LEN=*), INTENT(IN) :: hrough ! type of roughness length
90 LOGICAL, INTENT(IN) :: omeb ! True = patch with multi-energy balance
91 ! ! False = patch with classical ISBA
92 REAL, DIMENSION(:), INTENT(IN) :: palfa ! wind direction from J axis (clockwise)
93 REAL, DIMENSION(:), INTENT(IN) :: pzref ! height of atmospheric level
94 REAL, DIMENSION(:), INTENT(IN) :: puref ! reference height for wind
95 REAL, DIMENSION(:), INTENT(IN) :: pz0 ! vegetation roughness length
96 REAL, DIMENSION(:), INTENT(IN) :: pz0rel ! 1d orographic roughness length
97 REAL, DIMENSION(:), INTENT(IN) :: ppsn ! fraction of snow
98 REAL, DIMENSION(:), INTENT(IN) :: ppalphan ! snow/canopy transition coefficient
99 REAL, DIMENSION(:), INTENT(IN) :: pz0effip ! z0eff for increasing x
100 REAL, DIMENSION(:), INTENT(IN) :: pz0effim ! z0eff for decreasing x
101 REAL, DIMENSION(:), INTENT(IN) :: pz0effjp ! z0eff for increasing y
102 REAL, DIMENSION(:), INTENT(IN) :: pz0effjm ! z0eff for decreasing y
103 REAL, DIMENSION(:), INTENT(IN) :: paosip ! A/S for increasing x
104 REAL, DIMENSION(:), INTENT(IN) :: paosim ! A/S for decreasing x
105 REAL, DIMENSION(:), INTENT(IN) :: paosjp ! A/S for increasing y
106 REAL, DIMENSION(:), INTENT(IN) :: paosjm ! A/S for decreasing y
107 REAL, DIMENSION(:), INTENT(IN) :: pho2ip ! h/2 for increasing x
108 REAL, DIMENSION(:), INTENT(IN) :: pho2im ! h/2 for decreasing x
109 REAL, DIMENSION(:), INTENT(IN) :: pho2jp ! h/2 for increasing y
110 REAL, DIMENSION(:), INTENT(IN) :: pho2jm ! h/2 for decreasing y
111 REAL, DIMENSION(:), INTENT(IN) :: pz0_o_z0h ! ratio between heat and momentum z0
112 !
113 REAL, DIMENSION(:), INTENT(IN) :: pff ! fraction of flood
114 REAL, DIMENSION(:), INTENT(IN) :: pz0_flood ! floodplains roughness length
115 !
116 ! For multi-energy balance
117 REAL, DIMENSION(:), INTENT(IN) :: pz0litter ! ground litter roughness length for MEB
118 !
119 REAL, DIMENSION(:), INTENT(IN) :: pwsnow ! equivalent snow water content
120 !
121 REAL, DIMENSION(:), INTENT(OUT) :: pz0_with_snow ! vegetation z0 modified by snow
122 REAL, DIMENSION(:), INTENT(OUT) :: pz0h_with_snow ! vegetation z0h modified by snow
123 REAL, DIMENSION(:), INTENT(OUT) :: pz0eff ! effective z0
124 !
125 ! For multi-energy balance
126 REAL, DIMENSION(:), INTENT(OUT) :: pz0g_without_snow ! roughness length for momentum at snow-free canopy floor
127 !
128 REAL, DIMENSION(:), INTENT(OUT) :: pz0_mebv ! roughness length for momentum over MEB vegetation part of patch
129 REAL, DIMENSION(:), INTENT(OUT) :: pz0h_mebv ! roughness length for heat over MEB vegetation part of path
130 REAL, DIMENSION(:), INTENT(OUT) :: pz0eff_mebv ! roughness length for momentum over MEB vegetation part of patch
131 ! ! eventually including orograhic roughness
132 REAL, DIMENSION(:), INTENT(OUT) :: pz0_mebn ! roughness length for momentum over MEB snow part of patch
133 REAL, DIMENSION(:), INTENT(OUT) :: pz0h_mebn ! roughness length for heat over MEB snow part of path
134 REAL, DIMENSION(:), INTENT(OUT) :: pz0eff_mebn ! roughness length for momentum over MEB snow part of patch
135 !
136 !
137 !
138 !* 0.2 declarations of local variables
139 !
140 !
141 !
142 REAL, DIMENSION(SIZE(PZ0EFF)) :: zwork, zalfa, &
143  zz0effip, zz0effim, &
144  zz0effjp, zz0effjm, &
145  zpff
146 ! effective roughness length in 4
147 ! directions
148 REAL :: z0cr, zuz0cn, zalrcn1, zalrcn2
149 REAL(KIND=JPRB) :: zhook_handle
150 !-------------------------------------------------------------------------------
151 !
152 IF (lhook) CALL dr_hook('Z0EFF',0,zhook_handle)
153 zalrcn1=1.e-02
154 zalrcn2=2.5e-03
155 z0cr = zalrcn1
156 zuz0cn=1./zalrcn2
157 zalfa(:) = palfa(:)
158 WHERE(zalfa(:)<=-xpi) zalfa = zalfa + 2.*xpi
159 WHERE(zalfa(:)> xpi) zalfa = zalfa - 2.*xpi
160 !
161 ! Initialisation of MEB roughness lengths
162 pz0g_without_snow=0.
163 pz0_mebv=0.
164 pz0h_mebv=0.
165 pz0eff_mebv=0.
166 pz0_mebn=0.
167 pz0h_mebn=0.
168 pz0eff_mebn=0.
169 !
170 !* 1. GRID-AVERAGED ROUGHNESS LENGTHS
171 ! -------------------------------
172 ! (considering the effect of snow-flood-covered surfaces and orography)
173 !
174 !* 1.1 for heat
175 ! --------
176 !
177 pz0_with_snow(:) = pz0(:)
178 pz0h_with_snow(:) = pz0(:) / pz0_o_z0h(:)
179 !
180 IF(i%TSNOW%SCHEME=='EBA') THEN
181 !
182  WHERE (ppsn(:)>0.)
183 !
184 !!!!!Flooding scheme not implemented with this option
185  pz0_with_snow(:) = pz0_with_snow(:) + ( z0cr - pz0(:))* &
186  pwsnow(:)/(pwsnow(:) + xwcrn*(1.0+zuz0cn*pz0(:)))
187 !
188  END WHERE
189 
190 
191  IF (laldz0h) THEN
192  WHERE (ppsn(:)>0.)
193  pz0h_with_snow(:) = pz0h_with_snow(:) + ( z0cr - pz0h_with_snow(:))* &
194  pwsnow(:)/(pwsnow(:) + xwcrn*(1.0+zuz0cn*pz0h_with_snow(:)))
195  END WHERE
196  END IF
197 
198 !
199 ELSE
200 !
201  WHERE (ppsn(:)>0..OR.pff(:)>0.)
202 !
203  zwork(:) = ( ppsn(:) /(log(puref(:)/xz0sn ))**2 ) &
204  + ( pff(:) /(log(puref(:)/pz0_flood(:)))**2 ) &
205  + ((1.-ppsn(:)-pff(:))/(log(puref(:)/pz0(:) ))**2 )
206 !
207  pz0_with_snow(:) = puref(:) /exp( sqrt( 1./zwork(:) ) )
208 !
209  zwork(:) = ( ppsn(:) /(log(pzref(:)/xz0hsn ))**2 ) &
210  + ( pff(:) /(log(pzref(:)/(pz0_flood(:)/ pz0_o_z0h(:))))**2 ) &
211  + ((1.-ppsn(:)-pff(:))/(log(pzref(:)/(pz0(:)/pz0_o_z0h(:)) ))**2 )
212 !
213  pz0h_with_snow(:) = pzref(:) /exp( sqrt( 1./zwork(:) ) )
214 !
215  END WHERE
216 !
217 ENDIF
218 !
219 ! For multi-energy balance
220 IF(omeb)THEN
221 
222 ! roughness length for momentum at snow-free canopy floor
223  pz0g_without_snow(:) = pz0litter
224  WHERE (pff(:)>0.)
225  zpff(:)=pff(:)/(1-ppsn(:)+1.e-6)
226  zwork(:) = ( zpff(:) * log(pz0_flood(:)) ) &
227  + ( (1.-zpff(:)) * log(pz0litter(:)) )
228  pz0g_without_snow(:) = exp( zwork(:) )
229  END WHERE
230 !
231 ! roughness length for momentum over MEB vegetation part of patch
232  pz0_mebv(:) = pz0(:)
233 !
234 ! roughness length for momentum over MEB snow part of patch
235  zwork(:) = ( ppalphan(:) /(log(puref(:)/xz0sn ))**2 ) &
236  + ((1.-ppalphan(:))/(log(puref(:)/pz0_mebv(:) ))**2 )
237  pz0_mebn(:) = puref(:) /exp( sqrt( 1./zwork(:) ) )
238 !
239 
240 ! roughness length for momentum over MEB total patch
241  zwork(:) = ( ppsn(:) /(log(puref(:)/pz0_mebn(:) ))**2 ) &
242  + ((1.-ppsn(:))/(log(puref(:)/pz0_mebv(:) ))**2 )
243  pz0_with_snow(:) = puref(:) /exp( sqrt( 1./zwork(:) ) )
244 !
245 ! roughness length for heat over MEB vegetation part of path
246  pz0h_mebv(:) = pz0_mebv(:)/pz0_o_z0h(:)
247 ! for nordic forest, z0h=z0m according to M&#195;&#182;lder (tested in Hirlam):
248 !
249 ! PZ0H_MEBV(:) = PZ0_MEBV(:)
250 !
251 ! roughness length for heat over MEB snow part of path
252  zwork(:) = ( ppalphan(:) /(log(pzref(:)/xz0hsn ))**2 ) &
253  + ( (1.-ppalphan(:))/(log(pzref(:)/pz0h_mebv(:) ))**2 )
254  pz0h_mebn(:) = pzref(:) /exp( sqrt( 1./zwork(:) ) )
255 !
256 
257 ! roughness length for heat over MEB total path
258  zwork(:) = ( ppsn(:) /(log(pzref(:)/pz0h_mebn(:) ))**2 ) &
259  + ( (1.-ppsn(:))/(log(pzref(:)/pz0h_mebv(:) ))**2 )
260  pz0h_with_snow(:) = pzref(:) /exp( sqrt( 1./zwork(:) ) )
261 !
262 ENDIF
263 !
264 !* 1.2 for momentum
265 ! ------------
266 !
267 !
268 ! In this particular case, we now use
269 ! the roughness length due to the coupled
270 ! effect of vegetation and topography
271 ! Snow and Flood effects are yet taken
272 ! into account through ZZ0EFF
273 !
274 IF (hrough=='Z04D') THEN
275 !
276 ! For multi-energy balance (MEB): the HROUGH=='Z04D' option is not considered yet!
277  !
278  zz0effip(:) = pz0effip(:)
279  zz0effim(:) = pz0effim(:)
280  zz0effjp(:) = pz0effjp(:)
281  zz0effjm(:) = pz0effjm(:)
282  !
283  CALL subscale_z0eff(paosip,paosim,paosjp,paosjm, &
284  pho2ip,pho2im,pho2jp,pho2jm,pz0_with_snow, &
285  zz0effip,zz0effim,zz0effjp,zz0effjm, &
286  omask=(ppsn>0..OR.pff(:)>0.) )
287  !
288  WHERE(zalfa(:)>=0. .AND. zalfa(:)<xpi/2.)
289  pz0eff(:)=zz0effip(:)*sin(zalfa(:))**2 + zz0effjp(:)*cos(zalfa(:))**2
290  END WHERE
291  WHERE(zalfa(:)>=xpi/2. .AND. zalfa(:)<=xpi)
292  pz0eff(:)=zz0effip(:)*sin(zalfa(:))**2 + zz0effjm(:)*cos(zalfa(:))**2
293  END WHERE
294  WHERE (zalfa(:)>=-xpi/2 .AND. zalfa(:)<0.)
295  pz0eff(:)=zz0effim(:)*sin(zalfa(:))**2 + zz0effjp(:)*cos(zalfa(:))**2
296  END WHERE
297  WHERE (zalfa(:)>=-xpi .AND. zalfa(:)<-xpi/2.)
298  pz0eff(:)=zz0effim(:)*sin(zalfa(:))**2 + zz0effjm(:)*cos(zalfa(:))**2
299  END WHERE
300 !
301 ELSE IF (hrough=='Z01D') THEN
302  pz0eff(:) = pz0_with_snow(:) + pz0rel(:)
303  IF(omeb)THEN
304  pz0eff_mebv(:) = pz0_mebv(:) + pz0rel(:)
305  pz0eff_mebn(:) = pz0_mebn(:) + pz0rel(:)
306  ENDIF
307  IF (laldz0h) THEN
308  ! Aladin dynamic z0 contains already orographic component
309  pz0eff(:) = pz0eff(:) - pz0rel(:)
310  IF(omeb)THEN
311  pz0eff_mebv(:) = pz0eff_mebv(:) - pz0rel(:)
312  pz0eff_mebn(:) = pz0eff_mebn(:) - pz0rel(:)
313  ENDIF
314 ! PZ0H_WITH_SNOW(:) = PZ0EFF(:) / PZ0_O_Z0H(:) ! it is aleardy corrected under IF statement of TSNOW%SCHEME
315  ENDIF
316 ELSE
317  pz0eff(:) = pz0_with_snow(:)
318  IF(omeb)THEN
319  pz0eff_mebv(:) = pz0_mebv(:)
320  pz0eff_mebn(:) = pz0_mebn(:)
321  ENDIF
322 END IF
323 IF (lhook) CALL dr_hook('Z0EFF',1,zhook_handle)
324 !
325 !-------------------------------------------------------------------------------
326 !
327 END SUBROUTINE z0eff
subroutine z0eff(I, HROUGH, OMEB, PALFA, PZREF, PUREF, PZ0, PZ0REL, PPSN, PPALPHAN, PZ0LITTER, PWSNOW, PZ0EFFIP, PZ0EFFIM, PZ0EFFJP, PZ0EFFJM, PFF, PZ0_FLOOD, PAOSIP, PAOSIM, PAOSJP, PAOSJM, PHO2IP, PHO2IM, PHO2JP, PHO2JM, PZ0_O_Z0H, PZ0_WITH_SNOW, PZ0H_WITH_SNOW, PZ0EFF, PZ0G_WITHOUT_SNOW, PZ0_MEBV, PZ0H_MEBV, PZ0EFF_MEBV, PZ0_MEBN, PZ0H_MEBN, PZ0EFF_MEBN)
Definition: z0eff.F90:6