CCPP SciDoc v7.0.x  v7.0.0
Common Community Physics Package Developed at DTC
 
Loading...
Searching...
No Matches
sfc_nst.f90
1
3
5module sfc_nst
6
7 use machine , only : kind_phys, kp => kind_phys
8 use funcphys , only : fpvs
9 use module_nst_parameters , only : one, zero, half
10 use module_nst_parameters , only : t0k, cp_w, omg_m, omg_sh, sigma_r, solar_time_6am, sst_max
11 use module_nst_parameters , only : ri_c, z_w_max, delz, wd_max, rad2deg, const_rot, tau_min, tw_max
15 !
16 implicit none
17contains
18
27 subroutine sfc_nst_run &
28 ( im, hvap, cp, hfus, jcal, eps, epsm1, rvrdm1, rd, rhw0, & ! --- inputs:
29 pi, tgice, sbc, ps, u1, v1, usfco, vsfco, use_oceanuv, t1, &
30 q1, tref, cm, ch, lseaspray, fm, fm10, &
31 prsl1, prslki, prsik1, prslk1, wet, use_lake_model, xlon, &
32 sinlat, stress, &
33 sfcemis, dlwflx, sfcnsw, rain, timestep, kdt, solhr,xcosz, &
34 wind, flag_iter, flag_guess, nstf_name1, nstf_name4, &
35 nstf_name5, lprnt, ipr, thsfc_loc, &
36 tskin, tsurf, xt, xs, xu, xv, xz, zm, xtts, xzts, dt_cool, & ! --- input/output:
37 z_c, c_0, c_d, w_0, w_d, d_conv, ifd, qrain, &
38 qsurf, gflux, cmm, chh, evap, hflx, ep, errmsg, errflg & ! --- outputs:
39 )
40 !
41 ! ===================================================================== !
42 ! description: !
43 ! !
44 ! !
45 ! usage: !
46 ! !
47 ! call sfc_nst !
48 ! inputs: !
49 ! ( im, ps, u1, v1, t1, q1, tref, cm, ch, !
50 ! lseaspray, fm, fm10, !
51 ! prsl1, prslki, wet, use_lake_model, xlon, sinlat, stress, !
52 ! sfcemis, dlwflx, sfcnsw, rain, timestep, kdt,solhr,xcosz, !
53 ! wind, flag_iter, flag_guess, nstf_name1, nstf_name4, !
54 ! nstf_name5, lprnt, ipr, thsfc_loc, !
55 ! input/outputs: !
56 ! tskin, tsurf, xt, xs, xu, xv, xz, zm, xtts, xzts, dt_cool, !
57 ! z_c, c_0, c_d, w_0, w_d, d_conv, ifd, qrain, !
58 ! -- outputs:
59 ! qsurf, gflux, cmm, chh, evap, hflx, ep !
60 ! )
61 ! !
62 ! !
63 ! subprogram/functions called: fpvs, density, rhocoef, cool_skin !
64 ! !
65 ! program history log: !
66 ! 2007 -- xu li createad original code !
67 ! 2008 -- s. moorthi adapted to the parallel version !
68 ! may 2009 -- y.-t. hou modified to include input lw surface !
69 ! emissivity from radiation. also replaced the !
70 ! often comfusing combined sw and lw suface !
71 ! flux with separate sfc net sw flux (defined !
72 ! as dn-up) and lw flux. added a program doc block. !
73 ! sep 2009 -- s. moorthi removed rcl and additional reformatting !
74 ! and optimization + made pa as input pressure unit.!
75 ! 2009 -- xu li recreatead the code !
76 ! feb 2010 -- s. moorthi added some changes made to the previous !
77 ! version !
78 ! Jul 2016 -- X. Li, modify the diurnal warming event reset !
79 ! !
80 ! !
81 ! ==================== definition of variables ==================== !
82 ! !
83 ! inputs: size !
84 ! im - integer, horiz dimension 1 !
85 ! ps - real, surface pressure (pa) im !
86 ! u1, v1 - real, u/v component of surface layer wind (m/s) im !
87 ! usfco, vsfco - real, u/v component of surface current (m/s) im !
88 ! use_oceanuv - logical, option to include ocean surface 1 !
89 ! current in the computation of flux !
90 ! t1 - real, surface layer mean temperature ( k ) im !
91 ! q1 - real, surface layer mean specific humidity im !
92 ! tref - real, reference/foundation temperature ( k ) im !
93 ! cm - real, surface exchange coeff for momentum (m/s) im !
94 ! ch - real, surface exchange coeff heat & moisture(m/s) im !
95 ! lseaspray- logical, .t. for parameterization for sea spray 1 !
96 ! fm - real, a stability profile function for momentum im !
97 ! fm10 - real, a stability profile function for momentum im !
98 ! at 10m !
99 ! prsl1 - real, surface layer mean pressure (pa) im !
100 ! prslki - real, im !
101 ! prsik1 - real, im !
102 ! prslk1 - real, im !
103 ! wet - logical, =T if any ocn/lake water (F otherwise) im !
104 ! use_lake_model- logical, =T if flake model is used for lake im !
105 ! icy - logical, =T if any ice im !
106 ! xlon - real, longitude (radians) im !
107 ! sinlat - real, sin of latitude im !
108 ! stress - real, wind stress (n/m**2) im !
109 ! sfcemis - real, sfc lw emissivity (fraction) im !
110 ! dlwflx - real, total sky sfc downward lw flux (w/m**2) im !
111 ! sfcnsw - real, total sky sfc netsw flx into ocean (w/m**2) im !
112 ! rain - real, rainfall rate (kg/m**2/s) im !
113 ! timestep - real, timestep interval (second) 1 !
114 ! kdt - integer, time step counter 1 !
115 ! solhr - real, fcst hour at the end of prev time step 1 !
116 ! xcosz - real, consine of solar zenith angle 1 !
117 ! wind - real, wind speed (m/s) im !
118 ! flag_iter- logical, execution or not im !
119 ! when iter = 1, flag_iter = .true. for all grids im !
120 ! when iter = 2, flag_iter = .true. when wind < 2 im !
121 ! for both land and ocean (when nstf_name1 > 0) im !
122 ! flag_guess-logical, .true.= guess step to get CD et al im !
123 ! when iter = 1, flag_guess = .true. when wind < 2 im !
124 ! when iter = 2, flag_guess = .false. for all grids im !
125 ! nstf_name - integers , NSST related flag parameters 1 !
126 ! nstf_name1 : 0 = NSSTM off 1 !
127 ! 1 = NSSTM on but uncoupled 1 !
128 ! 2 = NSSTM on and coupled 1 !
129 ! nstf_name4 : zsea1 in mm 1 !
130 ! nstf_name5 : zsea2 in mm 1 !
131 ! lprnt - logical, control flag for check print out 1 !
132 ! ipr - integer, grid index for check print out 1 !
133 ! thsfc_loc- logical, flag for reference pressure in theta 1 !
134 ! !
135 ! input/outputs:
136 ! li added for oceanic components
137 ! tskin - real, ocean surface skin temperature ( k ) im !
138 ! tsurf - real, the same as tskin ( k ) but for guess run im !
139 ! xt - real, heat content in dtl im !
140 ! xs - real, salinity content in dtl im !
141 ! xu - real, u-current content in dtl im !
142 ! xv - real, v-current content in dtl im !
143 ! xz - real, dtl thickness im !
144 ! zm - real, mxl thickness im !
145 ! xtts - real, d(xt)/d(ts) im !
146 ! xzts - real, d(xz)/d(ts) im !
147 ! dt_cool - real, sub-layer cooling amount im !
148 ! d_conv - real, thickness of free convection layer (fcl) im !
149 ! z_c - sub-layer cooling thickness im !
150 ! c_0 - coefficient1 to calculate d(tz)/d(ts) im !
151 ! c_d - coefficient2 to calculate d(tz)/d(ts) im !
152 ! w_0 - coefficient3 to calculate d(tz)/d(ts) im !
153 ! w_d - coefficient4 to calculate d(tz)/d(ts) im !
154 ! ifd - real, index to start dtlm run or not im !
155 ! qrain - real, sensible heat flux due to rainfall (watts) im !
156
157 ! outputs: !
158
159 ! qsurf - real, surface air saturation specific humidity im !
160 ! gflux - real, soil heat flux (w/m**2) im !
161 ! cmm - real, im !
162 ! chh - real, im !
163 ! evap - real, evaperation from latent heat flux im !
164 ! hflx - real, sensible heat flux im !
165 ! ep - real, potential evaporation im !
166 ! !
167 ! ===================================================================== !
168
169
170
171 ! --- inputs:
172 integer, intent(in) :: im, kdt, ipr, nstf_name1, nstf_name4, nstf_name5
173 logical, intent(in) :: use_oceanuv
174
175 real (kind=kind_phys), intent(in) :: hvap, cp, hfus, jcal, eps, &
176 epsm1, rvrdm1, rd, rhw0, sbc, pi, tgice
177 real (kind=kind_phys), dimension(:), intent(in) :: ps, u1, v1, &
178 usfco, vsfco, t1, q1, cm, ch, fm, fm10, &
179 prsl1, prslki, prsik1, prslk1, xlon, xcosz, &
180 sinlat, stress, sfcemis, dlwflx, sfcnsw, rain, wind
181 real (kind=kind_phys), dimension(:), intent(in) :: tref
182 real (kind=kind_phys), intent(in) :: timestep
183 real (kind=kind_phys), intent(in) :: solhr
184
185 ! For sea spray effect
186 logical, intent(in) :: lseaspray
187 !
188 logical, dimension(:), intent(in) :: flag_iter, flag_guess, wet
189 integer, dimension(:), intent(in) :: use_lake_model
190 logical, intent(in) :: lprnt
191 logical, intent(in) :: thsfc_loc
192
193 ! --- input/outputs:
194 ! control variables of dtl system (5+2) and sl (2) and coefficients for d(tz)/d(ts) calculation
195 real (kind=kind_phys), dimension(:), intent(inout) :: tskin, &
196 tsurf
197 real (kind=kind_phys), dimension(:), intent(inout) :: &
198 xt, xs, xu, xv, xz, zm, xtts, xzts, dt_cool, &
199 z_c, c_0, c_d, w_0, w_d, d_conv, ifd, qrain
200
201 ! --- outputs:
202 real (kind=kind_phys), dimension(:), intent(inout) :: qsurf, gflux, cmm, chh, evap, hflx, ep
203
204 character(len=*), intent(out) :: errmsg
205 integer, intent(out) :: errflg
206
207 !
208 ! locals
209 !
210 integer :: k,i
211 !
212 real (kind=kind_phys), dimension(im) :: q0, qss, rch, rho_a, theta1, tv1, wndmag
213
214 real(kind=kind_phys) :: elocp,tem,cpinv,hvapi
215 !
216 ! nstm related prognostic fields
217 !
218 logical :: flag(im)
219 real (kind=kind_phys), dimension(im) :: xt_old, xs_old, xu_old, xv_old, xz_old, &
220 zm_old,xtts_old, xzts_old, ifd_old, tref_old, tskin_old, dt_cool_old,z_c_old
221
222 real(kind=kind_phys) :: ulwflx(im), nswsfc(im)
223 ! real(kind=kind_phys) rig(im),
224 ! & ulwflx(im),dlwflx(im),
225 ! & slrad(im),nswsfc(im)
226 real(kind=kind_phys) :: alpha,beta,rho_w,f_nsol,sss,sep, cosa,sina,taux,tauy, &
227 grav,dz,t0,ttop0,ttop
228
229 real(kind=kind_phys) :: le,fc,dwat,dtmp,wetc,alfac,ustar_a,rich
230 real(kind=kind_phys) :: rnl_ts,hs_ts,hl_ts,rf_ts,q_ts
231 real(kind=kind_phys) :: fw,q_warm
232 real(kind=kind_phys) :: t12,alon,tsea,sstc,dta,dtz
233 real(kind=kind_phys) :: zsea1,zsea2,soltim
234 logical :: do_nst
235 !
236 ! parameters for sea spray effect
237 !
238 real (kind=kind_phys) :: f10m, u10m, v10m, ws10, ru10, qss1, &
239 bb1, hflxs, evaps, ptem
240 !
241 ! real (kind=kind_phys), parameter :: alps=0.5, bets=0.5, gams=0.1,
242 ! real (kind=kind_phys), parameter :: alps=0.5, bets=0.5, gams=0.0,
243 ! real (kind=kind_phys), parameter :: alps=1.0, bets=1.0, gams=0.2,
244 real (kind=kind_phys), parameter :: alps=0.75,bets=0.75,gams=0.15, &
245 ws10cr=30., conlf=7.2e-9, consf=6.4e-8
246 real (kind=kind_phys) :: windrel
247 !
248 !======================================================================================================
249 ! Initialize CCPP error handling variables
250 errmsg = ''
251 errflg = 0
252
253 if (nstf_name1 == 0) return ! No NSST model used
254
255 cpinv = one/cp
256 hvapi = one/hvap
257 elocp = hvap/cp
258
259 sss = 34.0_kp ! temporarily, when sea surface salinity data is not ready
260 !
261 ! flag for open water and where the iteration is on
262 !
263 do_nst = .false.
264 do i = 1, im
265 ! flag(i) = wet(i) .and. .not.icy(i) .and. flag_iter(i)
266 flag(i) = wet(i) .and. flag_iter(i) .and. use_lake_model(i)/=1
267 do_nst = do_nst .or. flag(i)
268 enddo
269 if (.not. do_nst) return
270 !
271 ! save nst-related prognostic fields for guess run
272 !
273 do i=1, im
274 ! if(wet(i) .and. .not.icy(i) .and. flag_guess(i)) then
275 if(wet(i) .and. flag_guess(i) .and. use_lake_model(i)/=1) then
276 xt_old(i) = xt(i)
277 xs_old(i) = xs(i)
278 xu_old(i) = xu(i)
279 xv_old(i) = xv(i)
280 xz_old(i) = xz(i)
281 zm_old(i) = zm(i)
282 xtts_old(i) = xtts(i)
283 xzts_old(i) = xzts(i)
284 ifd_old(i) = ifd(i)
285 tskin_old(i) = tskin(i)
286 dt_cool_old(i) = dt_cool(i)
287 z_c_old(i) = z_c(i)
288 endif
289 enddo
290
291
292 ! --- ... initialize variables. all units are m.k.s. unless specified.
293 ! ps is in pascals, wind is wind speed, theta1 is surface air
294 ! estimated from level 1 temperature, rho_a is air density and
295 ! qss is saturation specific humidity at the water surface
296 !!
297 do i = 1, im
298 if ( flag(i) ) then
299
300 nswsfc(i) = sfcnsw(i) ! net solar radiation at the air-sea surface (positive downward)
301 wndmag(i) = sqrt(u1(i)*u1(i) + v1(i)*v1(i))
302
303 q0(i) = max(q1(i), 1.0e-8_kp)
304
305 if(thsfc_loc) then ! Use local potential temperature
306 theta1(i) = t1(i) * prslki(i)
307 else ! Use potential temperature referenced to 1000 hPa
308 theta1(i) = t1(i) / prslk1(i) ! potential temperature at the middle of lowest model layer
309 endif
310
311 tv1(i) = t1(i) * (one + rvrdm1*q0(i))
312 rho_a(i) = prsl1(i) / (rd*tv1(i))
313 qss(i) = fpvs(tsurf(i)) ! pa
314 qss(i) = eps*qss(i) / (ps(i) + epsm1*qss(i)) ! pa
315 !
316 evap(i) = zero
317 hflx(i) = zero
318 gflux(i) = zero
319 ep(i) = zero
320
321 ! --- ... rcp = rho cp ch v
322
323 if (use_oceanuv) then
324 windrel= sqrt( (u1(i)-usfco(i))**2 + (v1(i)-vsfco(i))**2 )
325 rch(i) = rho_a(i) * cp * ch(i) * windrel
326 cmm(i) = cm(i) * windrel
327 chh(i) = rho_a(i) * ch(i) * windrel
328 else
329 rch(i) = rho_a(i) * cp * ch(i) * wind(i)
330 cmm(i) = cm(i) * wind(i)
331 chh(i) = rho_a(i) * ch(i) * wind(i)
332 endif
333
335 ! at previous time step
336 evap(i) = elocp * rch(i) * (qss(i) - q0(i))
337 qsurf(i) = qss(i)
338
339 if(thsfc_loc) then ! Use local potential temperature
340 hflx(i) = rch(i) * (tsurf(i) - theta1(i))
341 else ! Use potential temperature referenced to 1000 hPa
342 hflx(i) = rch(i) * (tsurf(i)/prsik1(i) - theta1(i))
343 endif
344
345 ! if (lprnt .and. i == ipr) print *,' tskin=',tskin(i),' theta1=',
346 ! & theta1(i),' hflx=',hflx(i),' t1=',t1(i),'prslki=',prslki(i)
347 ! &,' tsurf=',tsurf(i)
348 endif
349 enddo
350
351 ! run nst model: dtm + slm
352 !
353 zsea1 = 0.001_kp*real(nstf_name4)
354 zsea2 = 0.001_kp*real(nstf_name5)
355
359 do i = 1, im
360 if ( flag(i) ) then
361 tsea = tsurf(i)
362 t12 = tsea*tsea
363 ulwflx(i) = sfcemis(i) * sbc * t12 * t12
364 alon = xlon(i)*rad2deg
365 grav = grv(sinlat(i))
366 soltim = mod(alon/15.0_kp + solhr, 24.0_kp)*3600.0_kp
367 call density(tsea,sss,rho_w) ! sea water density
368 call rhocoef(tsea,sss,rho_w,alpha,beta) ! alpha & beta
369 !
371 !
372 le = (2.501_kp-0.00237_kp*tsea)*1.0e6_kp
373 dwat = 2.11e-5_kp*(t1(i)/t0k)**1.94_kp ! water vapor diffusivity
374 dtmp = (one+3.309e-3_kp*(t1(i)-t0k)-1.44e-6_kp*(t1(i)-t0k) &
375 * (t1(i)-t0k))*0.02411_kp/(rho_a(i)*cp) ! heat diffusivity
376 wetc = 622.0_kp*le*qss(i)/(rd*t1(i)*t1(i))
377 alfac = one / (one + (wetc*le*dwat)/(cp*dtmp)) ! wet bulb factor
378 tem = (1.0e3_kp * rain(i) / rho_w) * alfac * cp_w
379 qrain(i) = tem * (tsea-t1(i)+1.0e3_kp*(qss(i)-q0(i))*le/cp)
380
382
383 f_nsol = hflx(i) + evap(i) + ulwflx(i) - dlwflx(i) + omg_sh*qrain(i)
384
385 ! if (lprnt .and. i == ipr) print *,' f_nsol=',f_nsol,' hflx=',
386 ! &hflx(i),' evap=',evap(i),' ulwflx=',ulwflx(i),' dlwflx=',dlwflx(i)
387 ! &,' omg_sh=',omg_sh,' qrain=',qrain(i)
388
389 sep = sss*(evap(i)/le-rain(i))/rho_w
390 ustar_a = sqrt(stress(i)/rho_a(i)) ! air friction velocity
391 !
392 ! sensitivities of heat flux components to ts
393 !
394 rnl_ts = 4.0_kp*sfcemis(i)*sbc*tsea*tsea*tsea ! d(rnl)/d(ts)
395 hs_ts = rch(i)
396 hl_ts = rch(i)*elocp*eps*hvap*qss(i)/(rd*t12)
397 rf_ts = tem * (one+rch(i)*hl_ts)
398 q_ts = rnl_ts + hs_ts + hl_ts + omg_sh*rf_ts
399 !
402 ! & calculate c_0, c_d
403 !
404 call cool_skin(ustar_a,f_nsol,nswsfc(i),evap(i),sss,alpha,beta, &
405 rho_w,rho_a(i),tsea,q_ts,hl_ts,grav,le, &
406 dt_cool(i),z_c(i),c_0(i),c_d(i))
407
408 tem = one / wndmag(i)
409 cosa = u1(i)*tem
410 sina = v1(i)*tem
411 taux = max(stress(i),tau_min)*cosa
412 tauy = max(stress(i),tau_min)*sina
413 fc = const_rot*sinlat(i)
414 !
415 ! Run DTM-1p system.
416 !
417 if ( (soltim > solar_time_6am .and. ifd(i) == zero) ) then
418 else
419 ifd(i) = one
420 !
421 ! calculate fcl thickness with current forcing and previous time's profile
422 !
423 ! if (lprnt .and. i == ipr) print *,' beg xz=',xz(i)
424
426 if ( f_nsol > zero .and. xt(i) > zero ) then
427 call convdepth(kdt,timestep,nswsfc(i),f_nsol,sss,sep,rho_w, &
428 alpha,beta,xt(i),xs(i),xz(i),d_conv(i))
429 else
430 d_conv(i) = zero
431 endif
432
433 ! if (lprnt .and. i == ipr) print *,' beg xz1=',xz(i)
434 !
435 ! determine rich: wind speed dependent (right now)
436 !
437 ! if ( wind(i) < 1.0 ) then
438 ! rich = 0.25 + 0.03*wind(i)
439 ! elseif ( wind(i) >= 1.0 .and. wind(i) < 1.5 ) then
440 ! rich = 0.25 + 0.1*wind(i)
441 ! elseif ( wind(i) >= 1.5 .and. wind(i) < 6.0 ) then
442 ! rich = 0.25 + 0.6*wind(i)
443 ! elseif ( wind(i) >= 6.0 ) then
444 ! rich = 0.25 + min(0.8*wind(i),0.50)
445 ! endif
446
447 rich = ri_c
448
450 call dtm_1p(kdt,timestep,rich,taux,tauy,nswsfc(i), &
451 f_nsol,sss,sep,q_ts,hl_ts,rho_w,alpha,beta,alon, &
452 sinlat(i),soltim,grav,le,d_conv(i), &
453 xt(i),xs(i),xu(i),xv(i),xz(i),xzts(i),xtts(i))
454
455 ! if (lprnt .and. i == ipr) print *,' beg xz2=',xz(i)
456
457 ! apply mda
458 if ( xt(i) > zero ) then
461 call dtm_1p_mda(xt(i),xtts(i),xz(i),xzts(i))
462 if ( xz(i) >= z_w_max ) then
465 call dtl_reset(xt(i),xs(i),xu(i),xv(i),xz(i),xtts(i), xzts(i))
466
467 ! if (lprnt .and. i == ipr) print *,' beg xz3=',xz(i),' z_w_max='
468 ! &,z_w_max
469 endif
470
471 ! apply fca
472 if ( d_conv(i) > zero .and. xt(i) > zero ) then
477 call dtm_1p_fca(d_conv(i),xt(i),xtts(i),xz(i),xzts(i))
478 if ( xz(i) >= z_w_max ) then
479 call dtl_reset (xt(i),xs(i),xu(i),xv(i),xz(i),xzts(i),xtts(i))
480 endif
481 endif
482
483 ! if (lprnt .and. i == ipr) print *,' beg xz4=',xz(i)
484
485 ! apply tla
486 dz = min(xz(i),max(d_conv(i),delz))
487 !
491 call sw_ps_9b(delz,fw)
492 q_warm = fw*nswsfc(i)-f_nsol !total heat absorbed in warm layer
493
496 if ( q_warm > zero ) then
497 call cal_ttop(kdt,timestep,q_warm,rho_w,dz, xt(i),xz(i),ttop0)
498
499 ! if (lprnt .and. i == ipr) print *,' d_conv=',d_conv(i),' delz=',
500 ! &delz,' kdt=',kdt,' timestep=',timestep,' nswsfc=',nswsfc(i),
501 ! &' f_nsol=',f_nsol,' rho_w=',rho_w,' dz=',dz,' xt=',xt(i),
502 ! &' xz=',xz(i),' qrain=',qrain(i)
503
504 ttop = ((xt(i)+xt(i))/xz(i))*(one-dz/((xz(i)+xz(i))))
505
506 ! if (lprnt .and. i == ipr) print *,' beg xz4a=',xz(i)
507 ! &,' ttop=',ttop,' ttop0=',ttop0,' xt=',xt(i),' dz=',dz
508 ! &,' xznew=',(xt(i)+sqrt(xt(i)*(xt(i)-dz*ttop0)))/ttop0
509
511 if ( ttop > ttop0 ) then
512 call dtm_1p_tla(dz,ttop0,xt(i),xtts(i),xz(i),xzts(i))
513
514 ! if (lprnt .and. i == ipr) print *,' beg xz4b=',xz(i),'z_w_max=',
515 ! &z_w_max
516 if ( xz(i) >= z_w_max ) then
517 call dtl_reset (xt(i),xs(i),xu(i),xv(i),xz(i),xzts(i),xtts(i))
518 endif
519 endif
520 endif ! if ( q_warm > 0.0 ) then
521
522 ! if (lprnt .and. i == ipr) print *,' beg xz5=',xz(i)
523
524 ! apply mwa
526 t0 = (xt(i)+xt(i))/xz(i)
527 if ( t0 > tw_max ) then
528 call dtm_1p_mwa(xt(i),xtts(i),xz(i),xzts(i))
529 if ( xz(i) >= z_w_max ) then
530 call dtl_reset (xt(i),xs(i),xu(i),xv(i),xz(i),xzts(i),xtts(i))
531 endif
532 endif
533
534 ! if (lprnt .and. i == ipr) print *,' beg xz6=',xz(i)
535
536 ! apply mta
538 sstc = tref(i) + (xt(i)+xt(i))/xz(i) - dt_cool(i)
539
540 if ( sstc > sst_max ) then
541 dta = sstc - sst_max
542 call dtm_1p_mta(dta,xt(i),xtts(i),xz(i),xzts(i))
543 ! write(*,'(a,f3.0,7f8.3)') 'mta, sstc,dta :',islimsk(i),
544 ! & sstc,dta,tref(i),xt(i),xz(i),2.0*xt(i)/xz(i),dt_cool(i)
545 if ( xz(i) >= z_w_max ) then
546 call dtl_reset (xt(i),xs(i),xu(i),xv(i),xz(i),xzts(i),xtts(i))
547 endif
548 endif
549 !
550 endif ! if ( xt(i) > 0.0 ) then
551 ! reset dtl at midnight and when solar zenith angle > 89.994 degree
552 if ( abs(soltim) < 2.0_kp*timestep ) then
553 call dtl_reset (xt(i),xs(i),xu(i),xv(i),xz(i),xzts(i),xtts(i))
554 endif
555
556 endif ! if (solar_time > solar_time_6am .and. ifd(i) == 0.0 ) then: too late to start the first day
557
558 ! if (lprnt .and. i == ipr) print *,' beg xz7=',xz(i)
559
560 ! update tsurf (when flag(i) .eqv. .true. )
562 call get_dtzm_point(xt(i),xz(i),dt_cool(i),z_c(i), zsea1,zsea2,dtz)
563 tsurf(i) = max(tgice, tref(i) + dtz )
564
565 ! if (lprnt .and. i == ipr) print *,' tsurf=',tsurf(i),' tref=',
566 ! &tref(i),' xz=',xz(i),' dt_cool=',dt_cool(i)
567
569 if ( xt(i) > zero ) then
570 call cal_w(kdt,xz(i),xt(i),xzts(i),xtts(i),w_0(i),w_d(i))
571 else
572 w_0(i) = zero
573 w_d(i) = zero
574 endif
575
576 ! if ( xt(i) > 0.0 ) then
577 ! rig(i) = grav*xz(i)*xz(i)*(alpha*xt(i)-beta*xs(i))
578 ! & /(2.0*(xu(i)*xu(i)+xv(i)*xv(i)))
579 ! else
580 ! rig(i) = 0.25
581 ! endif
582
583 ! qrain(i) = rig(i)
584 zm(i) = wind(i)
585
586 endif
587 enddo
588
589 ! restore nst-related prognostic fields for guess run
590 do i=1, im
591 ! if (wet(i) .and. .not.icy(i)) then
592 if (wet(i) .and. use_lake_model(i)/=1) then
593 if (flag_guess(i)) then ! when it is guess of
594 xt(i) = xt_old(i)
595 xs(i) = xs_old(i)
596 xu(i) = xu_old(i)
597 xv(i) = xv_old(i)
598 xz(i) = xz_old(i)
599 zm(i) = zm_old(i)
600 xtts(i) = xtts_old(i)
601 xzts(i) = xzts_old(i)
602 ifd(i) = ifd_old(i)
603 tskin(i) = tskin_old(i)
604 dt_cool(i) = dt_cool_old(i)
605 z_c(i) = z_c_old(i)
606 else
607 !
608 ! update tskin when coupled and not guess run
609 ! (all other NSST variables have been updated in this case)
610 !
611 if ( nstf_name1 > 1 ) then
612 tskin(i) = tsurf(i)
613 endif ! if nstf_name1 > 1 then
614 endif ! if flag_guess(i) then
615 endif ! if wet(i) .and. .not.icy(i) then
616 enddo
617
618 ! if (lprnt .and. i == ipr) print *,' beg xz8=',xz(i)
619
620 if ( nstf_name1 > 1 ) then
623 do i = 1, im
624 if ( flag(i) ) then
625 qss(i) = fpvs( tskin(i) )
626 qss(i) = eps*qss(i) / (ps(i) + epsm1*qss(i))
627 qsurf(i) = qss(i)
628 evap(i) = elocp*rch(i) * (qss(i) - q0(i))
629
630 if(thsfc_loc) then ! Use local potential temperature
631 hflx(i) = rch(i) * (tskin(i) - theta1(i))
632 else ! Use potential temperature referenced to 1000 hPa
633 hflx(i) = rch(i) * (tskin(i)/prsik1(i) - theta1(i))
634 endif
635
636 endif
637 enddo
638 endif ! if ( nstf_name1 > 1 ) then
639 !
641 !
642 do i=1,im
643 if(lseaspray .and. flag(i)) then
644 f10m = fm10(i) / fm(i)
645 u10m = f10m * u1(i)
646 v10m = f10m * v1(i)
647 ws10 = sqrt(u10m*u10m + v10m*v10m)
648 ws10 = max(ws10,1.)
649 ws10 = min(ws10,ws10cr)
650 tem = .015 * ws10 * ws10
651 ru10 = 1. - .087 * log(10./tem)
652 qss1 = fpvs(t1(i))
653 qss1 = eps * qss1 / (prsl1(i) + epsm1 * qss1)
654 tem = rd * cp * t1(i) * t1(i)
655 tem = 1. + eps * hvap * hvap * qss1 / tem
656 bb1 = 1. / tem
657 evaps = conlf * (ws10**5.4) * ru10 * bb1
658 evaps = evaps * rho_a(i) * hvap * (qss1 - q0(i))
659 evap(i) = evap(i) + alps * evaps
660 hflxs = consf * (ws10**3.4) * ru10
661 hflxs = hflxs * rho_a(i) * cp * (tskin(i) - t1(i))
662 ptem = alps - gams
663 hflx(i) = hflx(i) + bets * hflxs - ptem * evaps
664 endif
665 enddo
666 !
667 do i=1,im
668 if ( flag(i) ) then
669 tem = one / rho_a(i)
670 hflx(i) = hflx(i) * tem * cpinv
671 evap(i) = evap(i) * tem * hvapi
672 endif
673 enddo
674 !
675 ! if (lprnt) print *,' tskin=',tskin(ipr)
676
677 return
678 end subroutine sfc_nst_run
680end module sfc_nst
subroutine, public convdepth(kdt, timestep, i0, q, sss, sep, rho, alpha, beta, xt, xs, xz, d_conv)
This subroutine calculates depth for convective adjustment.
subroutine, public dtm_1p_mwa(xt, xtts, xz, xzts)
This subroutine applies maximum warming adjustment (mwa).
subroutine, public density(t, s, rho)
This subroutine computes sea water density.
subroutine, public dtm_1p_fca(d_conv, xt, xtts, xz, xzts)
This subroutine applies free convection adjustment(fca).
subroutine, public get_dtzm_point(xt, xz, dt_cool, zc, z1, z2, dtm)
This subroutine computes dtm (the mean of ).
subroutine, public cal_ttop(kdt, timestep, q_warm, rho, dz, xt, xz, ttop)
This subroutine calculates the diurnal warming amount at the top layer with thickness of delz.
subroutine, public dtm_1p_mta(dta, xt, xtts, xz, xzts)
This subroutine applies maximum temperature adjustment (mta).
subroutine, public dtm_1p(kdt, timestep, rich, tox, toy, i0, q, sss, sep, q_ts, hl_ts, rho, alpha, beta, alon, sinlat, soltim, grav, le, d_conv, xt, xs, xu, xv, xz, xzts, xtts)
This subroutine contains the module of diurnal thermocline layer model.
subroutine, public dtm_1p_mda(xt, xtts, xz, xzts)
This subroutine applies minimum depth adjustment (xz adjustment).
subroutine, public dtl_reset(xt, xs, xu, xv, xz, xzts, xtts)
This subroutine resets the value of xt,xs,xu,xv,xz,xtts,xzts.
subroutine, public rhocoef(t, s, rhoref, alpha, beta)
This subroutine computes thermal expansion coefficient (alpha) and saline contraction coefficient (be...
subroutine, public dtm_1p_tla(dz, te, xt, xtts, xz, xzts)
This subroutine applies top layer adjustment (tla).
subroutine, public cal_w(kdt, xz, xt, xzts, xtts, w_0, w_d)
This subroutine computes coefficients (w_0 and w_d) to calculate d(tw)/d(ts).
subroutine sfc_nst_run(im, hvap, cp, hfus, jcal, eps, epsm1, rvrdm1, rd, rhw0, pi, tgice, sbc, ps, u1, v1, usfco, vsfco, use_oceanuv, t1, q1, tref, cm, ch, lseaspray, fm, fm10, prsl1, prslki, prsik1, prslk1, wet, use_lake_model, xlon, sinlat, stress, sfcemis, dlwflx, sfcnsw, rain, timestep, kdt, solhr, xcosz, wind, flag_iter, flag_guess, nstf_name1, nstf_name4, nstf_name5, lprnt, ipr, thsfc_loc, tskin, tsurf, xt, xs, xu, xv, xz, zm, xtts, xzts, dt_cool, z_c, c_0, c_d, w_0, w_d, d_conv, ifd, qrain, qsurf, gflux, cmm, chh, evap, hflx, ep, errmsg, errflg)
Definition sfc_nst.f90:40
subroutine, public cool_skin(ustar_a, f_nsol, f_sol_0, evap, sss, alpha, beta, rho_w, rho_a, ts, q_ts, hl_ts, grav, le, deltat_c, z_c, c_0, c_d)
This subroutine contains the upper ocean cool-skin parameterization (Fairall et al,...
real(kind_phys) function, public grv(x)
This module contains constants and parameters used in GFS near surface sea temperature scheme.
This module contains GFS NSST water property subroutines.
This module contains the diurnal thermocline layer model (DTM) of the GFS NSST scheme.
This module contains the CCPP-compliant GFS near-surface sea temperature scheme.
Definition sfc_nst.f90:5