source: LMDZ6/branches/Amaury_dev/libf/phylmd/conccm.F90 @ 5146

Last change on this file since 5146 was 5144, checked in by abarral, 11 months ago

Put YOMCST.h into modules

  • Property copyright set to
    Name of program: LMDZ
    Creation date: 1984
    Version: LMDZ5
    License: CeCILL version 2
    Holder: Laboratoire de m\'et\'eorologie dynamique, CNRS, UMR 8539
    See the license file in the root directory
  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 28.7 KB
Line 
1! $Header$
2
3SUBROUTINE conccm(dtime, paprs, pplay, t, q, conv_q, d_t, d_q, rain, snow, &
4        kbascm, ktopcm)
5
6  USE dimphy
7  USE lmdz_yoethf
8  USE lmdz_yomcst
9
10  IMPLICIT NONE
11  ! ======================================================================
12  ! Auteur(s): Z.X. Li (LMD/CNRS) date: le 14 mars 1996
13  ! Objet: Schema simple (avec flux de masse) pour la convection
14  ! (schema standard du modele NCAR CCM2)
15  ! ======================================================================
16
17  ! Entree:
18  REAL dtime ! pas d'integration
19  REAL paprs(klon, klev + 1) ! pression inter-couche (Pa)
20  REAL pplay(klon, klev) ! pression au milieu de couche (Pa)
21  REAL t(klon, klev) ! temperature (K)
22  REAL q(klon, klev) ! humidite specifique (g/g)
23  REAL conv_q(klon, klev) ! taux de convergence humidite (g/g/s)
24  ! Sortie:
25  REAL d_t(klon, klev) ! incrementation temperature
26  REAL d_q(klon, klev) ! incrementation vapeur
27  REAL rain(klon) ! pluie (mm/s)
28  REAL snow(klon) ! neige (mm/s)
29  INTEGER kbascm(klon) ! niveau du bas de convection
30  INTEGER ktopcm(klon) ! niveau du haut de convection
31
32  REAL pt(klon, klev)
33  REAL pq(klon, klev)
34  REAL pres(klon, klev)
35  REAL dp(klon, klev)
36  REAL zgeom(klon, klev)
37  REAL cmfprs(klon)
38  REAL cmfprt(klon)
39  INTEGER ntop(klon)
40  INTEGER nbas(klon)
41  INTEGER i, k
42  REAL zlvdcp, zlsdcp, zdelta, zz, za, zb
43
44  LOGICAL usekuo ! utiliser convection profonde (schema Kuo)
45  PARAMETER (usekuo = .TRUE.)
46
47  REAL d_t_bis(klon, klev)
48  REAL d_q_bis(klon, klev)
49  REAL rain_bis(klon)
50  REAL snow_bis(klon)
51  INTEGER ibas_bis(klon)
52  INTEGER itop_bis(klon)
53  REAL d_ql_bis(klon, klev)
54  REAL rneb_bis(klon, klev)
55
56  ! initialiser les variables de sortie (pour securite)
57  DO i = 1, klon
58    rain(i) = 0.0
59    snow(i) = 0.0
60    kbascm(i) = 0
61    ktopcm(i) = 0
62  END DO
63  DO k = 1, klev
64    DO i = 1, klon
65      d_t(i, k) = 0.0
66      d_q(i, k) = 0.0
67    END DO
68  END DO
69
70  ! preparer les variables d'entree (attention: l'ordre des niveaux
71  ! verticaux augmente du haut vers le bas)
72  DO k = 1, klev
73    DO i = 1, klon
74      pt(i, k) = t(i, klev - k + 1)
75      pq(i, k) = q(i, klev - k + 1)
76      pres(i, k) = pplay(i, klev - k + 1)
77      dp(i, k) = paprs(i, klev + 1 - k) - paprs(i, klev + 1 - k + 1)
78    END DO
79  END DO
80  DO i = 1, klon
81    zgeom(i, klev) = rd * t(i, 1) / (0.5 * (paprs(i, 1) + pplay(i, &
82            1))) * (paprs(i, 1) - pplay(i, 1))
83  END DO
84  DO k = 2, klev
85    DO i = 1, klon
86      zgeom(i, klev + 1 - k) = zgeom(i, klev + 1 - k + 1) + rd * 0.5 * (t(i, k - 1) + t(i, k)) / &
87              paprs(i, k) * (pplay(i, k - 1) - pplay(i, k))
88    END DO
89  END DO
90
91  CALL cmfmca(dtime, pres, dp, zgeom, pt, pq, cmfprt, cmfprs, ntop, nbas)
92
93  DO k = 1, klev
94    DO i = 1, klon
95      d_q(i, klev + 1 - k) = pq(i, k) - q(i, klev + 1 - k)
96      d_t(i, klev + 1 - k) = pt(i, k) - t(i, klev + 1 - k)
97    END DO
98  END DO
99
100  DO i = 1, klon
101    rain(i) = cmfprt(i) * rhoh2o
102    snow(i) = cmfprs(i) * rhoh2o
103    kbascm(i) = klev + 1 - nbas(i)
104    ktopcm(i) = klev + 1 - ntop(i)
105  END DO
106
107  IF (usekuo) THEN
108    CALL conkuo(dtime, paprs, pplay, t, q, conv_q, d_t_bis, d_q_bis, &
109            d_ql_bis, rneb_bis, rain_bis, snow_bis, ibas_bis, itop_bis)
110    DO k = 1, klev
111      DO i = 1, klon
112        d_t(i, k) = d_t(i, k) + d_t_bis(i, k)
113        d_q(i, k) = d_q(i, k) + d_q_bis(i, k)
114      END DO
115    END DO
116    DO i = 1, klon
117      rain(i) = rain(i) + rain_bis(i)
118      snow(i) = snow(i) + snow_bis(i)
119      kbascm(i) = min(kbascm(i), ibas_bis(i))
120      ktopcm(i) = max(ktopcm(i), itop_bis(i))
121    END DO
122    DO k = 1, klev ! eau liquide convective est
123      DO i = 1, klon ! dispersee dans l'air
124        zlvdcp = rlvtt / rcpd / (1.0 + rvtmp2 * q(i, k))
125        zlsdcp = rlstt / rcpd / (1.0 + rvtmp2 * q(i, k))
126        zdelta = max(0., sign(1., rtt - t(i, k)))
127        zz = d_ql_bis(i, k) ! re-evap. de l'eau liquide
128        zb = max(0.0, zz)
129        za = -max(0.0, zz) * (zlvdcp * (1. - zdelta) + zlsdcp * zdelta)
130        d_t(i, k) = d_t(i, k) + za
131        d_q(i, k) = d_q(i, k) + zb
132      END DO
133    END DO
134  END IF
135
136END SUBROUTINE conccm
137SUBROUTINE cmfmca(deltat, p, dp, gz, tb, shb, cmfprt, cmfprs, cnt, cnb)
138  USE dimphy
139  USE lmdz_yoethf
140  USE lmdz_fcttre, ONLY: foeew, foede, qsats, qsatl, dqsats, dqsatl, thermcep
141  USE lmdz_yomcst
142
143  IMPLICIT NONE
144  ! -----------------------------------------------------------------------
145  ! Moist convective mass flux procedure:
146  ! If stratification is unstable to nonentraining parcel ascent,
147  ! complete an adjustment making use of a simple cloud model
148
149  ! Code generalized to allow specification of parcel ("updraft")
150  ! properties, as well as convective transport of an arbitrary
151  ! number of passive constituents (see cmrb array).
152  ! ----------------------------Code History-------------------------------
153  ! Original version:  J. J. Hack, March 22, 1990
154  ! Standardized:      J. Rosinski, June 1992
155  ! Reviewed:          J. Hack, G. Taylor, August 1992
156  ! Adaptation au LMD: Z.X. Li, mars 1996 (reference: Hack 1994,
157  ! J. Geophys. Res. vol 99, D3, 5551-5568). J'ai
158  ! introduit les constantes et les fonctions thermo-
159  ! dynamiques du Centre Europeen. J'ai elimine le
160  ! re-indicage du code en esperant que cela pourra
161  ! simplifier la lecture et la comprehension.
162  ! -----------------------------------------------------------------------
163  INTEGER pcnst ! nombre de traceurs passifs
164  PARAMETER (pcnst = 1)
165  ! ------------------------------Arguments--------------------------------
166  ! Input arguments
167
168  REAL deltat ! time step (seconds)
169  REAL p(klon, klev) ! pressure
170  REAL dp(klon, klev) ! delta-p
171  REAL gz(klon, klev) ! geopotential (a partir du sol)
172
173  REAL thtap(klon) ! PBL perturbation theta
174  REAL shp(klon) ! PBL perturbation specific humidity
175  REAL pblh(klon) ! PBL height (provided by PBL routine)
176  REAL cmrp(klon, pcnst) ! constituent perturbations in PBL
177
178  ! Updated arguments:
179
180  REAL tb(klon, klev) ! temperature (t bar)
181  REAL shb(klon, klev) ! specific humidity (sh bar)
182  REAL cmrb(klon, klev, pcnst) ! constituent mixing ratios (cmr bar)
183
184  ! Output arguments
185
186  REAL cmfdt(klon, klev) ! dT/dt due to moist convection
187  REAL cmfdq(klon, klev) ! dq/dt due to moist convection
188  REAL cmfmc(klon, klev) ! moist convection cloud mass flux
189  REAL cmfdqr(klon, klev) ! dq/dt due to convective rainout
190  REAL cmfsl(klon, klev) ! convective lw static energy flux
191  REAL cmflq(klon, klev) ! convective total water flux
192  REAL cmfprt(klon) ! convective precipitation rate
193  REAL cmfprs(klon) ! convective snowfall rate
194  REAL qc(klon, klev) ! dq/dt due to rainout terms
195  INTEGER cnt(klon) ! top level of convective activity
196  INTEGER cnb(klon) ! bottom level of convective activity
197  ! ------------------------------Parameters-------------------------------
198  REAL c0 ! rain water autoconversion coefficient
199  PARAMETER (c0 = 1.0E-4)
200  REAL dzmin ! minimum convective depth for precipitation
201  PARAMETER (dzmin = 0.0)
202  REAL betamn ! minimum overshoot parameter
203  PARAMETER (betamn = 0.10)
204  REAL cmftau ! characteristic adjustment time scale
205  PARAMETER (cmftau = 3600.)
206  INTEGER limcnv ! top interface level limit for convection
207  PARAMETER (limcnv = 1)
208  REAL tpmax ! maximum acceptable t perturbation (degrees C)
209  PARAMETER (tpmax = 1.50)
210  REAL shpmax ! maximum acceptable q perturbation (g/g)
211  PARAMETER (shpmax = 1.50E-3)
212  REAL tiny ! arbitrary small num used in transport estimates
213  PARAMETER (tiny = 1.0E-36)
214  REAL eps ! convergence criteria (machine dependent)
215  PARAMETER (eps = 1.0E-13)
216  REAL tmelt ! freezing point of water(req'd for rain vs snow)
217  PARAMETER (tmelt = 273.15)
218  REAL ssfac ! supersaturation bound (detrained air)
219  PARAMETER (ssfac = 1.001)
220
221  ! ---------------------------Local workspace-----------------------------
222  REAL gam(klon, klev) ! L/cp (d(qsat)/dT)
223  REAL sb(klon, klev) ! dry static energy (s bar)
224  REAL hb(klon, klev) ! moist static energy (h bar)
225  REAL shbs(klon, klev) ! sat. specific humidity (sh bar star)
226  REAL hbs(klon, klev) ! sat. moist static energy (h bar star)
227  REAL shbh(klon, klev + 1) ! specific humidity on interfaces
228  REAL sbh(klon, klev + 1) ! s bar on interfaces
229  REAL hbh(klon, klev + 1) ! h bar on interfaces
230  REAL cmrh(klon, klev + 1) ! interface constituent mixing ratio
231  REAL prec(klon) ! instantaneous total precipitation
232  REAL dzcld(klon) ! depth of convective layer (m)
233  REAL beta(klon) ! overshoot parameter (fraction)
234  REAL betamx ! local maximum on overshoot
235  REAL eta(klon) ! convective mass flux (kg/m^2 s)
236  REAL etagdt ! eta*grav*deltat
237  REAL cldwtr(klon) ! cloud water (mass)
238  REAL rnwtr(klon) ! rain water  (mass)
239  REAL sc(klon) ! dry static energy   ("in-cloud")
240  REAL shc(klon) ! specific humidity   ("in-cloud")
241  REAL hc(klon) ! moist static energy ("in-cloud")
242  REAL cmrc(klon) ! constituent mix rat ("in-cloud")
243  REAL dq1(klon) ! shb  convective change (lower lvl)
244  REAL dq2(klon) ! shb  convective change (mid level)
245  REAL dq3(klon) ! shb  convective change (upper lvl)
246  REAL ds1(klon) ! sb   convective change (lower lvl)
247  REAL ds2(klon) ! sb   convective change (mid level)
248  REAL ds3(klon) ! sb   convective change (upper lvl)
249  REAL dcmr1(klon) ! cmrb convective change (lower lvl)
250  REAL dcmr2(klon) ! cmrb convective change (mid level)
251  REAL dcmr3(klon) ! cmrb convective change (upper lvl)
252  REAL flotab(klon) ! hc - hbs (mesure d'instabilite)
253  LOGICAL ldcum(klon) ! .TRUE. si la convection existe
254  LOGICAL etagt0 ! true if eta > 0.0
255  REAL dt ! current 2 delta-t (model time step)
256  REAL cats ! modified characteristic adj. time
257  REAL rdt ! 1./dt
258  REAL qprime ! modified specific humidity pert.
259  REAL tprime ! modified thermal perturbation
260  REAL pblhgt ! bounded pbl height (max[pblh,1m])
261  REAL fac1 ! intermediate scratch variable
262  REAL shprme ! intermediate specific humidity pert.
263  REAL qsattp ! saturation mixing ratio for
264  !  thermally perturbed PBL parcels
265  REAL dz ! local layer depth
266  REAL b1 ! bouyancy measure in detrainment lvl
267  REAL b2 ! bouyancy measure in condensation lvl
268  REAL g ! bounded vertical gradient of hb
269  REAL tmass ! total mass available for convective exchange
270  REAL denom ! intermediate scratch variable
271  REAL qtest1 ! used in negative q test (middle lvl)
272  REAL qtest2 ! used in negative q test (lower lvl)
273  REAL fslkp ! flux lw static energy (bot interface)
274  REAL fslkm ! flux lw static energy (top interface)
275  REAL fqlkp ! flux total water (bottom interface)
276  REAL fqlkm ! flux total water (top interface)
277  REAL botflx ! bottom constituent mixing ratio flux
278  REAL topflx ! top constituent mixing ratio flux
279  REAL efac1 ! ratio cmrb to convectively induced change (bot lvl)
280  REAL efac2 ! ratio cmrb to convectively induced change (mid lvl)
281  REAL efac3 ! ratio cmrb to convectively induced change (top lvl)
282
283  INTEGER i, k ! indices horizontal et vertical
284  INTEGER km1 ! k-1 (index offset)
285  INTEGER kp1 ! k+1 (index offset)
286  INTEGER m ! constituent index
287  INTEGER ktp ! temporary index used to track top
288  INTEGER is ! nombre de points a ajuster
289
290  REAL tmp1, tmp2, tmp3, tmp4
291  REAL zx_t, zx_p, zx_q, zx_qs, zx_gam
292  REAL zcor, zdelta, zcvm5
293
294  REAL qhalf, sh1, sh2, shbs1, shbs2
295  qhalf(sh1, sh2, shbs1, shbs2) = min(max(sh1, sh2), &
296          (shbs2 * sh1 + shbs1 * sh2) / (shbs1 + shbs2))
297
298  ! -----------------------------------------------------------------------
299  ! pas de traceur pour l'instant
300  DO m = 1, pcnst
301    DO k = 1, klev
302      DO i = 1, klon
303        cmrb(i, k, m) = 0.0
304      END DO
305    END DO
306  END DO
307
308  ! Les perturbations de la couche limite sont zero pour l'instant
309
310  DO m = 1, pcnst
311    DO i = 1, klon
312      cmrp(i, m) = 0.0
313    END DO
314  END DO
315  DO i = 1, klon
316    thtap(i) = 0.0
317    shp(i) = 0.0
318    pblh(i) = 1.0
319  END DO
320
321  ! Ensure that characteristic adjustment time scale (cmftau) assumed
322  ! in estimate of eta isn't smaller than model time scale (deltat)
323
324  dt = deltat
325  cats = max(dt, cmftau)
326  rdt = 1.0 / dt
327
328  ! Compute sb,hb,shbs,hbs
329
330  DO k = 1, klev
331    DO i = 1, klon
332      zx_t = tb(i, k)
333      zx_p = p(i, k)
334      zx_q = shb(i, k)
335      zdelta = max(0., sign(1., rtt - zx_t))
336      zcvm5 = r5les * rlvtt * (1. - zdelta) + r5ies * rlstt * zdelta
337      zcvm5 = zcvm5 / rcpd / (1.0 + rvtmp2 * zx_q)
338      zx_qs = r2es * foeew(zx_t, zdelta) / zx_p
339      zx_qs = min(0.5, zx_qs)
340      zcor = 1. / (1. - retv * zx_qs)
341      zx_qs = zx_qs * zcor
342      zx_gam = foede(zx_t, zdelta, zcvm5, zx_qs, zcor)
343      shbs(i, k) = zx_qs
344      gam(i, k) = zx_gam
345    END DO
346  END DO
347
348  DO k = limcnv, klev
349    DO i = 1, klon
350      sb(i, k) = rcpd * tb(i, k) + gz(i, k)
351      hb(i, k) = sb(i, k) + rlvtt * shb(i, k)
352      hbs(i, k) = sb(i, k) + rlvtt * shbs(i, k)
353    END DO
354  END DO
355
356  ! Compute sbh, shbh
357
358  DO k = limcnv + 1, klev
359    km1 = k - 1
360    DO i = 1, klon
361      sbh(i, k) = 0.5 * (sb(i, km1) + sb(i, k))
362      shbh(i, k) = qhalf(shb(i, km1), shb(i, k), shbs(i, km1), shbs(i, k))
363      hbh(i, k) = sbh(i, k) + rlvtt * shbh(i, k)
364    END DO
365  END DO
366
367  ! Specify properties at top of model (not used, but filling anyway)
368
369  DO i = 1, klon
370    sbh(i, limcnv) = sb(i, limcnv)
371    shbh(i, limcnv) = shb(i, limcnv)
372    hbh(i, limcnv) = hb(i, limcnv)
373  END DO
374
375  ! Zero vertically independent control, tendency & diagnostic arrays
376
377  DO i = 1, klon
378    prec(i) = 0.0
379    dzcld(i) = 0.0
380    cnb(i) = 0
381    cnt(i) = klev + 1
382  END DO
383
384  DO k = 1, klev
385    DO i = 1, klon
386      cmfdt(i, k) = 0.
387      cmfdq(i, k) = 0.
388      cmfdqr(i, k) = 0.
389      cmfmc(i, k) = 0.
390      cmfsl(i, k) = 0.
391      cmflq(i, k) = 0.
392    END DO
393  END DO
394
395  ! Begin moist convective mass flux adjustment procedure.
396  ! Formalism ensures that negative cloud liquid water can never occur
397
398  DO k = klev - 1, limcnv + 1, -1
399    km1 = k - 1
400    kp1 = k + 1
401    DO i = 1, klon
402      eta(i) = 0.0
403      beta(i) = 0.0
404      ds1(i) = 0.0
405      ds2(i) = 0.0
406      ds3(i) = 0.0
407      dq1(i) = 0.0
408      dq2(i) = 0.0
409      dq3(i) = 0.0
410
411      ! Specification of "cloud base" conditions
412
413      qprime = 0.0
414      tprime = 0.0
415
416      ! Assign tprime within the PBL to be proportional to the quantity
417      ! thtap (which will be bounded by tpmax), passed to this routine by
418      ! the PBL routine.  Don't allow perturbation to produce a dry
419      ! adiabatically unstable parcel.  Assign qprime within the PBL to be
420      ! an appropriately modified value of the quantity shp (which will be
421      ! bounded by shpmax) passed to this routine by the PBL routine.  The
422      ! quantity qprime should be less than the local saturation value
423      ! (qsattp=qsat[t+tprime,p]).  In both cases, thtap and shp are
424      ! linearly reduced toward zero as the PBL top is approached.
425
426      pblhgt = max(pblh(i), 1.0)
427      IF (gz(i, kp1) / rg<=pblhgt .AND. dzcld(i)==0.0) THEN
428        fac1 = max(0.0, 1.0 - gz(i, kp1) / rg / pblhgt)
429        tprime = min(thtap(i), tpmax) * fac1
430        qsattp = shbs(i, kp1) + rcpd / rlvtt * gam(i, kp1) * tprime
431        shprme = min(min(shp(i), shpmax) * fac1, max(qsattp - shb(i, kp1), 0.0))
432        qprime = max(qprime, shprme)
433      ELSE
434        tprime = 0.0
435        qprime = 0.0
436      END IF
437
438      ! Specify "updraft" (in-cloud) thermodynamic properties
439
440      sc(i) = sb(i, kp1) + rcpd * tprime
441      shc(i) = shb(i, kp1) + qprime
442      hc(i) = sc(i) + rlvtt * shc(i)
443      flotab(i) = hc(i) - hbs(i, k)
444      dz = dp(i, k) * rd * tb(i, k) / rg / p(i, k)
445      IF (flotab(i)>0.0) THEN
446        dzcld(i) = dzcld(i) + dz
447      ELSE
448        dzcld(i) = 0.0
449      END IF
450    END DO
451
452    ! Check on moist convective instability
453
454    is = 0
455    DO i = 1, klon
456      IF (flotab(i)>0.0) THEN
457        ldcum(i) = .TRUE.
458        is = is + 1
459      ELSE
460        ldcum(i) = .FALSE.
461      END IF
462    END DO
463
464    IF (is==0) THEN
465      DO i = 1, klon
466        dzcld(i) = 0.0
467      END DO
468      GO TO 70
469    END IF
470
471    ! Current level just below top level => no overshoot
472
473    IF (k<=limcnv + 1) THEN
474      DO i = 1, klon
475        IF (ldcum(i)) THEN
476          cldwtr(i) = sb(i, k) - sc(i) + flotab(i) / (1.0 + gam(i, k))
477          cldwtr(i) = max(0.0, cldwtr(i))
478          beta(i) = 0.0
479        END IF
480      END DO
481      GO TO 20
482    END IF
483
484    ! First guess at overshoot parameter using crude buoyancy closure
485    ! 10% overshoot assumed as a minimum and 1-c0*dz maximum to start
486    ! If pre-existing supersaturation in detrainment layer, beta=0
487    ! cldwtr is temporarily equal to RLVTT*l (l=> liquid water)
488
489    DO i = 1, klon
490      IF (ldcum(i)) THEN
491        cldwtr(i) = sb(i, k) - sc(i) + flotab(i) / (1.0 + gam(i, k))
492        cldwtr(i) = max(0.0, cldwtr(i))
493        betamx = 1.0 - c0 * max(0.0, (dzcld(i) - dzmin))
494        b1 = (hc(i) - hbs(i, km1)) * dp(i, km1)
495        b2 = (hc(i) - hbs(i, k)) * dp(i, k)
496        beta(i) = max(betamn, min(betamx, 1.0 + b1 / b2))
497        IF (hbs(i, km1)<=hb(i, km1)) beta(i) = 0.0
498      END IF
499    END DO
500
501    ! Bound maximum beta to ensure physically realistic solutions
502
503    ! First check constrains beta so that eta remains positive
504    ! (assuming that eta is already positive for beta equal zero)
505    ! La premiere contrainte de beta est que le flux eta doit etre positif.
506
507    DO i = 1, klon
508      IF (ldcum(i)) THEN
509        tmp1 = (1.0 + gam(i, k)) * (sc(i) - sbh(i, kp1) + cldwtr(i)) - &
510                (hbh(i, kp1) - hc(i)) * dp(i, k) / dp(i, kp1)
511        tmp2 = (1.0 + gam(i, k)) * (sc(i) - sbh(i, k))
512        IF ((beta(i) * tmp2 - tmp1)>0.0) THEN
513          betamx = 0.99 * (tmp1 / tmp2)
514          beta(i) = max(0.0, min(betamx, beta(i)))
515        END IF
516
517        ! Second check involves supersaturation of "detrainment layer"
518        ! small amount of supersaturation acceptable (by ssfac factor)
519        ! La 2e contrainte est que la convection ne doit pas sursaturer
520        ! la "detrainment layer", Neanmoins, une petite sursaturation
521        ! est acceptee (facteur ssfac).
522
523        IF (hb(i, km1)<hbs(i, km1)) THEN
524          tmp1 = (1.0 + gam(i, k)) * (sc(i) - sbh(i, kp1) + cldwtr(i)) - &
525                  (hbh(i, kp1) - hc(i)) * dp(i, k) / dp(i, kp1)
526          tmp1 = tmp1 / dp(i, k)
527          tmp2 = gam(i, km1) * (sbh(i, k) - sc(i) + cldwtr(i)) - hbh(i, k) + hc(i) - &
528                  sc(i) + sbh(i, k)
529          tmp3 = (1.0 + gam(i, k)) * (sc(i) - sbh(i, k)) / dp(i, k)
530          tmp4 = (dt / cats) * (hc(i) - hbs(i, k)) * tmp2 / (dp(i, km1) * (hbs(i, km1) - hb(i, &
531                  km1))) + tmp3
532          IF ((beta(i) * tmp4 - tmp1)>0.0) THEN
533            betamx = ssfac * (tmp1 / tmp4)
534            beta(i) = max(0.0, min(betamx, beta(i)))
535          END IF
536        ELSE
537          beta(i) = 0.0
538        END IF
539
540        ! Third check to avoid introducing 2 delta x thermodynamic
541        ! noise in the vertical ... constrain adjusted h (or theta e)
542        ! so that the adjustment doesn't contribute to "kinks" in h
543
544        g = min(0.0, hb(i, k) - hb(i, km1))
545        tmp3 = (hb(i, k) - hb(i, km1) - g) * (cats / dt) / (hc(i) - hbs(i, k))
546        tmp1 = (1.0 + gam(i, k)) * (sc(i) - sbh(i, kp1) + cldwtr(i)) - &
547                (hbh(i, kp1) - hc(i)) * dp(i, k) / dp(i, kp1)
548        tmp1 = tmp1 / dp(i, k)
549        tmp1 = tmp3 * tmp1 + (hc(i) - hbh(i, kp1)) / dp(i, k)
550        tmp2 = tmp3 * (1.0 + gam(i, k)) * (sc(i) - sbh(i, k)) / dp(i, k) + &
551                (hc(i) - hbh(i, k) - cldwtr(i)) * (1.0 / dp(i, k) + 1.0 / dp(i, kp1))
552        IF ((beta(i) * tmp2 - tmp1)>0.0) THEN
553          betamx = 0.0
554          IF (tmp2/=0.0) betamx = tmp1 / tmp2
555          beta(i) = max(0.0, min(betamx, beta(i)))
556        END IF
557      END IF
558    END DO
559
560    ! Calculate mass flux required for stabilization.
561
562    ! Ensure that the convective mass flux, eta, is positive by
563    ! setting negative values of eta to zero..
564    ! Ensure that estimated mass flux cannot move more than the
565    ! minimum of total mass contained in either layer k or layer k+1.
566    ! Also test for other pathological cases that result in non-
567    ! physical states and adjust eta accordingly.
568
569    20  CONTINUE
570    DO i = 1, klon
571      IF (ldcum(i)) THEN
572        beta(i) = max(0.0, beta(i))
573        tmp1 = hc(i) - hbs(i, k)
574        tmp2 = ((1.0 + gam(i, k)) * (sc(i) - sbh(i, kp1) + cldwtr(i)) - beta(i) * (1.0 + gam(&
575                i, k)) * (sc(i) - sbh(i, k))) / dp(i, k) - (hbh(i, kp1) - hc(i)) / dp(i, kp1)
576        eta(i) = tmp1 / (tmp2 * rg * cats)
577        tmass = min(dp(i, k), dp(i, kp1)) / rg
578        IF (eta(i)>tmass * rdt .OR. eta(i)<=0.0) eta(i) = 0.0
579
580        ! Check on negative q in top layer (bound beta)
581
582        IF (shc(i) - shbh(i, k)<0.0 .AND. beta(i) * eta(i)/=0.0) THEN
583          denom = eta(i) * rg * dt * (shc(i) - shbh(i, k)) / dp(i, km1)
584          beta(i) = max(0.0, min(-0.999 * shb(i, km1) / denom, beta(i)))
585        END IF
586
587        ! Check on negative q in middle layer (zero eta)
588
589        qtest1 = shb(i, k) + eta(i) * rg * dt * ((shc(i) - shbh(i, &
590                kp1)) - (1.0 - beta(i)) * cldwtr(i) / rlvtt - beta(i) * (shc(i) - shbh(i, &
591                k))) / dp(i, k)
592        IF (qtest1<=0.0) eta(i) = 0.0
593
594        ! Check on negative q in lower layer (bound eta)
595
596        fac1 = -(shbh(i, kp1) - shc(i)) / dp(i, kp1)
597        qtest2 = shb(i, kp1) - eta(i) * rg * dt * fac1
598        IF (qtest2<0.0) THEN
599          eta(i) = 0.99 * shb(i, kp1) / (rg * dt * fac1)
600        END IF
601      END IF
602    END DO
603
604
605    ! Calculate cloud water, rain water, and thermodynamic changes
606
607    DO i = 1, klon
608      IF (ldcum(i)) THEN
609        etagdt = eta(i) * rg * dt
610        cldwtr(i) = etagdt * cldwtr(i) / rlvtt / rg
611        rnwtr(i) = (1.0 - beta(i)) * cldwtr(i)
612        ds1(i) = etagdt * (sbh(i, kp1) - sc(i)) / dp(i, kp1)
613        dq1(i) = etagdt * (shbh(i, kp1) - shc(i)) / dp(i, kp1)
614        ds2(i) = (etagdt * (sc(i) - sbh(i, kp1)) + rlvtt * rg * cldwtr(i) - beta(i) * etagdt &
615                * (sc(i) - sbh(i, k))) / dp(i, k)
616        dq2(i) = (etagdt * (shc(i) - shbh(i, kp1)) - rg * rnwtr(i) - beta(i) * etagdt * (shc &
617                (i) - shbh(i, k))) / dp(i, k)
618        ds3(i) = beta(i) * (etagdt * (sc(i) - sbh(i, k)) - rlvtt * rg * cldwtr(i)) / dp(i, &
619                km1)
620        dq3(i) = beta(i) * etagdt * (shc(i) - shbh(i, k)) / dp(i, km1)
621
622        ! Isolate convective fluxes for later diagnostics
623
624        fslkp = eta(i) * (sc(i) - sbh(i, kp1))
625        fslkm = beta(i) * (eta(i) * (sc(i) - sbh(i, k)) - rlvtt * cldwtr(i) * rdt)
626        fqlkp = eta(i) * (shc(i) - shbh(i, kp1))
627        fqlkm = beta(i) * eta(i) * (shc(i) - shbh(i, k))
628
629
630        ! Update thermodynamic profile (update sb, hb, & hbs later)
631
632        tb(i, kp1) = tb(i, kp1) + ds1(i) / rcpd
633        tb(i, k) = tb(i, k) + ds2(i) / rcpd
634        tb(i, km1) = tb(i, km1) + ds3(i) / rcpd
635        shb(i, kp1) = shb(i, kp1) + dq1(i)
636        shb(i, k) = shb(i, k) + dq2(i)
637        shb(i, km1) = shb(i, km1) + dq3(i)
638        prec(i) = prec(i) + rnwtr(i) / rhoh2o
639
640        ! Update diagnostic information for final budget
641        ! Tracking temperature & specific humidity tendencies,
642        ! rainout term, convective mass flux, convective liquid
643        ! water static energy flux, and convective total water flux
644
645        cmfdt(i, kp1) = cmfdt(i, kp1) + ds1(i) / rcpd * rdt
646        cmfdt(i, k) = cmfdt(i, k) + ds2(i) / rcpd * rdt
647        cmfdt(i, km1) = cmfdt(i, km1) + ds3(i) / rcpd * rdt
648        cmfdq(i, kp1) = cmfdq(i, kp1) + dq1(i) * rdt
649        cmfdq(i, k) = cmfdq(i, k) + dq2(i) * rdt
650        cmfdq(i, km1) = cmfdq(i, km1) + dq3(i) * rdt
651        cmfdqr(i, k) = cmfdqr(i, k) + (rg * rnwtr(i) / dp(i, k)) * rdt
652        cmfmc(i, kp1) = cmfmc(i, kp1) + eta(i)
653        cmfmc(i, k) = cmfmc(i, k) + beta(i) * eta(i)
654        cmfsl(i, kp1) = cmfsl(i, kp1) + fslkp
655        cmfsl(i, k) = cmfsl(i, k) + fslkm
656        cmflq(i, kp1) = cmflq(i, kp1) + rlvtt * fqlkp
657        cmflq(i, k) = cmflq(i, k) + rlvtt * fqlkm
658        qc(i, k) = (rg * rnwtr(i) / dp(i, k)) * rdt
659      END IF
660    END DO
661
662    ! Next, convectively modify passive constituents
663
664    DO m = 1, pcnst
665      DO i = 1, klon
666        IF (ldcum(i)) THEN
667
668          ! If any of the reported values of the constituent is negative in
669          ! the three adjacent levels, nothing will be done to the profile
670
671          IF ((cmrb(i, kp1, m)<0.0) .OR. (cmrb(i, k, m)<0.0) .OR. (cmrb(i, km1, &
672                  m)<0.0)) GO TO 40
673
674          ! Specify constituent interface values (linear interpolation)
675
676          cmrh(i, k) = 0.5 * (cmrb(i, km1, m) + cmrb(i, k, m))
677          cmrh(i, kp1) = 0.5 * (cmrb(i, k, m) + cmrb(i, kp1, m))
678
679          ! Specify perturbation properties of constituents in PBL
680
681          pblhgt = max(pblh(i), 1.0)
682          IF (gz(i, kp1) / rg<=pblhgt .AND. dzcld(i)==0.) THEN
683            fac1 = max(0.0, 1.0 - gz(i, kp1) / rg / pblhgt)
684            cmrc(i) = cmrb(i, kp1, m) + cmrp(i, m) * fac1
685          ELSE
686            cmrc(i) = cmrb(i, kp1, m)
687          END IF
688
689          ! Determine fluxes, flux divergence => changes due to convection
690          ! Logic must be included to avoid producing negative values. A bit
691          ! messy since there are no a priori assumptions about profiles.
692          ! Tendency is modified (reduced) when pending disaster detected.
693
694          etagdt = eta(i) * rg * dt
695          botflx = etagdt * (cmrc(i) - cmrh(i, kp1))
696          topflx = beta(i) * etagdt * (cmrc(i) - cmrh(i, k))
697          dcmr1(i) = -botflx / dp(i, kp1)
698          efac1 = 1.0
699          efac2 = 1.0
700          efac3 = 1.0
701
702          IF (cmrb(i, kp1, m) + dcmr1(i)<0.0) THEN
703            efac1 = max(tiny, abs(cmrb(i, kp1, m) / dcmr1(i)) - eps)
704          END IF
705
706          IF (efac1==tiny .OR. efac1>1.0) efac1 = 0.0
707          dcmr1(i) = -efac1 * botflx / dp(i, kp1)
708          dcmr2(i) = (efac1 * botflx - topflx) / dp(i, k)
709
710          IF (cmrb(i, k, m) + dcmr2(i)<0.0) THEN
711            efac2 = max(tiny, abs(cmrb(i, k, m) / dcmr2(i)) - eps)
712          END IF
713
714          IF (efac2==tiny .OR. efac2>1.0) efac2 = 0.0
715          dcmr2(i) = (efac1 * botflx - efac2 * topflx) / dp(i, k)
716          dcmr3(i) = efac2 * topflx / dp(i, km1)
717
718          IF (cmrb(i, km1, m) + dcmr3(i)<0.0) THEN
719            efac3 = max(tiny, abs(cmrb(i, km1, m) / dcmr3(i)) - eps)
720          END IF
721
722          IF (efac3==tiny .OR. efac3>1.0) efac3 = 0.0
723          efac3 = min(efac2, efac3)
724          dcmr2(i) = (efac1 * botflx - efac3 * topflx) / dp(i, k)
725          dcmr3(i) = efac3 * topflx / dp(i, km1)
726
727          cmrb(i, kp1, m) = cmrb(i, kp1, m) + dcmr1(i)
728          cmrb(i, k, m) = cmrb(i, k, m) + dcmr2(i)
729          cmrb(i, km1, m) = cmrb(i, km1, m) + dcmr3(i)
730        END IF
731      40    END DO
732    END DO ! end of m=1,pcnst loop
733
734    IF (k==limcnv + 1) GO TO 60 ! on ne pourra plus glisser
735
736    ! Dans la procedure de glissage ascendant, les variables thermo-
737    ! dynamiques des couches k et km1 servent au calcul des couches
738    ! superieures. Elles ont donc besoin d'une mise-a-jour.
739
740    DO i = 1, klon
741      IF (ldcum(i)) THEN
742        zx_t = tb(i, k)
743        zx_p = p(i, k)
744        zx_q = shb(i, k)
745        zdelta = max(0., sign(1., rtt - zx_t))
746        zcvm5 = r5les * rlvtt * (1. - zdelta) + r5ies * rlstt * zdelta
747        zcvm5 = zcvm5 / rcpd / (1.0 + rvtmp2 * zx_q)
748        zx_qs = r2es * foeew(zx_t, zdelta) / zx_p
749        zx_qs = min(0.5, zx_qs)
750        zcor = 1. / (1. - retv * zx_qs)
751        zx_qs = zx_qs * zcor
752        zx_gam = foede(zx_t, zdelta, zcvm5, zx_qs, zcor)
753        shbs(i, k) = zx_qs
754        gam(i, k) = zx_gam
755
756        zx_t = tb(i, km1)
757        zx_p = p(i, km1)
758        zx_q = shb(i, km1)
759        zdelta = max(0., sign(1., rtt - zx_t))
760        zcvm5 = r5les * rlvtt * (1. - zdelta) + r5ies * rlstt * zdelta
761        zcvm5 = zcvm5 / rcpd / (1.0 + rvtmp2 * zx_q)
762        zx_qs = r2es * foeew(zx_t, zdelta) / zx_p
763        zx_qs = min(0.5, zx_qs)
764        zcor = 1. / (1. - retv * zx_qs)
765        zx_qs = zx_qs * zcor
766        zx_gam = foede(zx_t, zdelta, zcvm5, zx_qs, zcor)
767        shbs(i, km1) = zx_qs
768        gam(i, km1) = zx_gam
769
770        sb(i, k) = sb(i, k) + ds2(i)
771        sb(i, km1) = sb(i, km1) + ds3(i)
772        hb(i, k) = sb(i, k) + rlvtt * shb(i, k)
773        hb(i, km1) = sb(i, km1) + rlvtt * shb(i, km1)
774        hbs(i, k) = sb(i, k) + rlvtt * shbs(i, k)
775        hbs(i, km1) = sb(i, km1) + rlvtt * shbs(i, km1)
776
777        sbh(i, k) = 0.5 * (sb(i, k) + sb(i, km1))
778        shbh(i, k) = qhalf(shb(i, km1), shb(i, k), shbs(i, km1), shbs(i, k))
779        hbh(i, k) = sbh(i, k) + rlvtt * shbh(i, k)
780        sbh(i, km1) = 0.5 * (sb(i, km1) + sb(i, k - 2))
781        shbh(i, km1) = qhalf(shb(i, k - 2), shb(i, km1), shbs(i, k - 2), &
782                shbs(i, km1))
783        hbh(i, km1) = sbh(i, km1) + rlvtt * shbh(i, km1)
784      END IF
785    END DO
786
787    ! Ensure that dzcld is reset if convective mass flux zero
788    ! specify the current vertical extent of the convective activity
789    ! top of convective layer determined by size of overshoot param.
790
791    60  CONTINUE
792    DO i = 1, klon
793      etagt0 = eta(i) > 0.0
794      IF (.NOT. etagt0) dzcld(i) = 0.0
795      IF (etagt0 .AND. beta(i)>betamn) THEN
796        ktp = km1
797      ELSE
798        ktp = k
799      END IF
800      IF (etagt0) THEN
801        cnt(i) = min(cnt(i), ktp)
802        cnb(i) = max(cnb(i), k)
803      END IF
804    END DO
805  70 END DO ! end of k loop
806
807  ! determine whether precipitation, prec, is frozen (snow) or not
808
809  DO i = 1, klon
810    IF (tb(i, klev)<tmelt .AND. tb(i, klev - 1)<tmelt) THEN
811      cmfprs(i) = prec(i) * rdt
812    ELSE
813      cmfprt(i) = prec(i) * rdt
814    END IF
815  END DO
816
817  RETURN ! we're all done ... return to calling procedure
818END SUBROUTINE cmfmca
Note: See TracBrowser for help on using the repository browser.