Skip to content

Commit 13896df

Browse files
committed
fix terminal velocity computations for pedmf; use only positive mass for the computations
1 parent 4fbc052 commit 13896df

File tree

1 file changed

+87
-43
lines changed

1 file changed

+87
-43
lines changed

src/cache/precipitation_precomputed_quantities.jl

Lines changed: 87 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,12 @@ function Kin(ᶜw_precip, ᶜu_air)
3131
)
3232
end
3333

34+
"""
35+
Smallest mass value that is different than zero for the purpose of mass_weigthed
36+
averaging of terminal velocities.
37+
"""
38+
ϵ_numerics(FT) = sqrt(floatmin(FT))
39+
3440
"""
3541
set_precipitation_velocities!(Y, p, moisture_model, microphysics_model, turbconv_model)
3642
@@ -120,11 +126,13 @@ function set_precipitation_velocities!(
120126
ᶜρa⁰ = @. lazy(ρa⁰(Y.c.ρ, Y.c.sgsʲs, turbconv_model))
121127
n = n_mass_flux_subdomains(turbconv_model)
122128

123-
# scratch to compute env velocities
124-
ᶜw⁰ = p.scratch.ᶜtemp_scalar
129+
# scratch to compute env mass flux
130+
ᶜimplied_env_mass_flux = p.scratch.ᶜtemp_scalar
125131
# scratch to add positive masses of subdomains
126132
# TODO use Y.c.ρq instead of ᶜρχ for computing gs velocities by averaging velocities
127-
# over subdomains once negative subdomain mass issues are resolved
133+
# over subdomains once negative subdomain mass issues are resolved
134+
# We use positive masses for mass-weighted averaging gs terminal velocity. This ensures
135+
# that the value remains between sgs terminal velocity values (important for stability).
128136
ᶜρχ = p.scratch.ᶜtemp_scalar_2
129137
# scratch for adding energy fluxes over subdomains
130138
ᶜρwₕhₜ = p.scratch.ᶜtemp_scalar_3
@@ -138,76 +146,112 @@ function set_precipitation_velocities!(
138146
ᶜq_sno⁰ = ᶜspecific_env_value(@name(q_sno), Y, p)
139147

140148
# Cloud liquid
141-
@. ᶜw⁰ = CMNe.terminal_velocity(
149+
ᶜρa⁰χ⁰ = @. lazy(max(zero(Y.c.ρ), ᶜρa⁰) * max(zero(Y.c.ρ), ᶜq_liq⁰))
150+
@. ᶜρχ = ᶜρa⁰χ⁰
151+
@. ᶜwₗ = ᶜρa⁰χ⁰ * CMNe.terminal_velocity(
142152
cmc.liquid,
143153
cmc.Ch2022.rain,
144154
ᶜρ⁰,
145-
max(zero(Y.c.ρ), ᶜq_liq⁰),
155+
ᶜq_liq⁰,
146156
)
147-
@. ᶜwₗ = ᶜρa⁰ * ᶜq_liq⁰ * ᶜw⁰
148-
@. ᶜρχ = max(zero(Y.c.ρ), ᶜρa⁰ * ᶜq_liq⁰)
157+
@. ᶜimplied_env_mass_flux = 0
158+
# add updraft contributions
149159
for j in 1:n
150-
@. ᶜwₗ += Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_liq * ᶜwₗʲs.:($$j)
151-
@. ᶜρχ += max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_liq)
160+
ᶜρaʲχʲ = @. lazy(
161+
max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).ρa) *
162+
max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).q_liq),
163+
)
164+
@. ᶜρχ += ᶜρaʲχʲ
165+
@. ᶜwₗ += ᶜρaʲχʲ * ᶜwₗʲs.:($$j)
166+
@. ᶜimplied_env_mass_flux -=
167+
Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_liq * ᶜwₗʲs.:($$j)
152168
end
153-
@. ᶜwₗ = ifelse(ᶜρχ > FT(0), ᶜwₗ / ᶜρχ, FT(0))
154-
155-
# contribution of env cloud liquid advection to htot advection
156-
@. ᶜρwₕhₜ = ᶜρa⁰ * ᶜq_liq⁰ * ᶜw⁰ * (Iₗ(thp, ᶜts⁰) + ᶜΦ)
169+
# average
170+
@. ᶜwₗ = ifelse(ᶜρχ > ϵ_numerics(FT), ᶜwₗ / ᶜρχ, FT(0))
171+
@. ᶜimplied_env_mass_flux += Y.c.ρq_liq * ᶜwₗ
172+
# contribution of env q_liq sedimentation to htot
173+
@. ᶜρwₕhₜ = ᶜimplied_env_mass_flux * (Iₗ(thp, ᶜts⁰) + ᶜΦ)
157174

158175
# Cloud ice
159-
@. ᶜw⁰ = CMNe.terminal_velocity(
176+
ᶜρa⁰χ⁰ = @. lazy(max(zero(Y.c.ρ), ᶜρa⁰) * max(zero(Y.c.ρ), ᶜq_ice⁰))
177+
@. ᶜρχ = ᶜρa⁰χ⁰
178+
@. ᶜwᵢ = ᶜρa⁰χ⁰ * CMNe.terminal_velocity(
160179
cmc.ice,
161180
cmc.Ch2022.small_ice,
162181
ᶜρ⁰,
163-
max(zero(Y.c.ρ), ᶜq_ice⁰),
182+
ᶜq_ice⁰,
164183
)
165-
@. ᶜwᵢ = ᶜρa⁰ * ᶜq_ice⁰ * ᶜw⁰
166-
@. ᶜρχ = max(zero(Y.c.ρ), ᶜρa⁰ * ᶜq_ice⁰)
184+
@. ᶜimplied_env_mass_flux = 0
185+
# add updraft contributions
167186
for j in 1:n
168-
@. ᶜwᵢ += Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_ice * ᶜwᵢʲs.:($$j)
169-
@. ᶜρχ += max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_ice)
187+
ᶜρaʲχʲ = @. lazy(
188+
max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).ρa) *
189+
max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).q_ice),
190+
)
191+
@. ᶜρχ += ᶜρaʲχʲ
192+
@. ᶜwᵢ += ᶜρaʲχʲ * ᶜwᵢʲs.:($$j)
193+
@. ᶜimplied_env_mass_flux -=
194+
Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_ice * ᶜwᵢʲs.:($$j)
170195
end
171-
@. ᶜwᵢ = ifelse(ᶜρχ > FT(0), ᶜwᵢ / ᶜρχ, FT(0))
172-
173-
# contribution of env cloud ice advection to htot advection
174-
@. ᶜρwₕhₜ += ᶜρa⁰ * ᶜq_ice⁰ * ᶜw⁰ * (Iᵢ(thp, ᶜts⁰) + ᶜΦ)
196+
# average
197+
@. ᶜwᵢ = ifelse(ᶜρχ > ϵ_numerics(FT), ᶜwᵢ / ᶜρχ, FT(0))
198+
@. ᶜimplied_env_mass_flux += Y.c.ρq_ice * ᶜwᵢ
199+
# contribution of env q_liq sedimentation to htot
200+
@. ᶜρwₕhₜ += ᶜimplied_env_mass_flux * (Iᵢ(thp, ᶜts⁰) + ᶜΦ)
175201

176202
# Rain
177-
@. ᶜw⁰ = CM1.terminal_velocity(
203+
ᶜρa⁰χ⁰ = @. lazy(max(zero(Y.c.ρ), ᶜρa⁰) * max(zero(Y.c.ρ), ᶜq_rai⁰))
204+
@. ᶜρχ = ᶜρa⁰χ⁰
205+
@. ᶜwᵣ = ᶜρa⁰χ⁰ * CM1.terminal_velocity(
178206
cmp.pr,
179207
cmp.tv.rain,
180208
ᶜρ⁰,
181-
max(zero(Y.c.ρ), ᶜq_rai⁰),
209+
ᶜq_rai⁰,
182210
)
183-
@. ᶜwᵣ = ᶜρa⁰ * ᶜq_rai⁰ * ᶜw⁰
184-
@. ᶜρχ = max(zero(Y.c.ρ), ᶜρa⁰ * ᶜq_rai⁰)
211+
@. ᶜimplied_env_mass_flux = 0
212+
# add updraft contributions
185213
for j in 1:n
186-
@. ᶜwᵣ += Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_rai * ᶜwᵣʲs.:($$j)
187-
@. ᶜρχ += max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_rai)
214+
ᶜρaʲχʲ = @. lazy(
215+
max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).ρa) *
216+
max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).q_rai),
217+
)
218+
@. ᶜρχ += ᶜρaʲχʲ
219+
@. ᶜwᵣ += ᶜρaʲχʲ * ᶜwᵣʲs.:($$j)
220+
@. ᶜimplied_env_mass_flux -=
221+
Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_rai * ᶜwᵣʲs.:($$j)
188222
end
189-
@. ᶜwᵣ = ifelse(ᶜρχ > FT(0), ᶜwᵣ / ᶜρχ, FT(0))
190-
191-
# contribution of env rain advection to htot advection
192-
@. ᶜρwₕhₜ += ᶜρa⁰ * ᶜq_rai⁰ * ᶜw⁰ * (Iₗ(thp, ᶜts⁰) + ᶜΦ)
223+
# average
224+
@. ᶜwᵣ = ifelse(ᶜρχ > ϵ_numerics(FT), ᶜwᵣ / ᶜρχ, FT(0))
225+
@. ᶜimplied_env_mass_flux += Y.c.ρq_rai * ᶜwᵣ
226+
# contribution of env q_liq sedimentation to htot
227+
@. ᶜρwₕhₜ += ᶜimplied_env_mass_flux * (Iₗ(thp, ᶜts⁰) + ᶜΦ)
193228

194229
# Snow
195-
@. ᶜw⁰ = CM1.terminal_velocity(
230+
ᶜρa⁰χ⁰ = @. lazy(max(zero(Y.c.ρ), ᶜρa⁰) * max(zero(Y.c.ρ), ᶜq_sno⁰))
231+
@. ᶜρχ = ᶜρa⁰χ⁰
232+
@. ᶜwₛ = ᶜρa⁰χ⁰ * CM1.terminal_velocity(
196233
cmp.ps,
197234
cmp.tv.snow,
198235
ᶜρ⁰,
199-
max(zero(Y.c.ρ), ᶜq_sno⁰),
236+
ᶜq_sno⁰,
200237
)
201-
@. ᶜwₛ = ᶜρa⁰ * ᶜq_sno⁰ * ᶜw⁰
202-
@. ᶜρχ = max(zero(Y.c.ρ), ᶜρa⁰ * ᶜq_sno⁰)
238+
@. ᶜimplied_env_mass_flux = 0
239+
# add updraft contributions
203240
for j in 1:n
204-
@. ᶜwₛ += Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_sno * ᶜwₛʲs.:($$j)
205-
@. ᶜρχ += max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_sno)
241+
ᶜρaʲχʲ = @. lazy(
242+
max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).ρa) *
243+
max(zero(Y.c.ρ), Y.c.sgsʲs.:($$j).q_sno),
244+
)
245+
@. ᶜρχ += ᶜρaʲχʲ
246+
@. ᶜwₛ += ᶜρaʲχʲ * ᶜwₛʲs.:($$j)
247+
@. ᶜimplied_env_mass_flux -=
248+
Y.c.sgsʲs.:($$j).ρa * Y.c.sgsʲs.:($$j).q_sno * ᶜwₛʲs.:($$j)
206249
end
207-
@. ᶜwₛ = ifelse(ᶜρχ > FT(0), ᶜwₛ / ᶜρχ, FT(0))
208-
209-
# contribution of env snow advection to htot advection
210-
@. ᶜρwₕhₜ += ᶜρa⁰ * ᶜq_sno⁰ * ᶜw⁰ * (Iᵢ(thp, ᶜts⁰) + ᶜΦ)
250+
# average
251+
@. ᶜwₛ = ifelse(ᶜρχ > ϵ_numerics(FT), ᶜwₛ / ᶜρχ, FT(0))
252+
@. ᶜimplied_env_mass_flux += Y.c.ρq_sno * ᶜwₛ
253+
# contribution of env q_liq sedimentation to htot
254+
@. ᶜρwₕhₜ += ᶜimplied_env_mass_flux * (Iᵢ(thp, ᶜts⁰) + ᶜΦ)
211255

212256
# Add contributions to energy and total water advection
213257
# TODO do we need to add kinetic energy of subdomains?

0 commit comments

Comments
 (0)