|
3 | 3 | #####
|
4 | 4 |
|
5 | 5 | import Thermodynamics as TD
|
6 |
| -import ClimaCore.Spaces as Spaces |
7 | 6 | import ClimaCore.Fields as Fields
|
8 |
| -import ClimaCore.Operators as Operators |
9 |
| - |
10 |
| -##### |
11 |
| -##### No subsidence |
12 |
| -##### |
13 |
| - |
14 |
| -subsidence_tendency!(Yₜ, Y, p, t, ::Nothing) = nothing |
15 | 7 |
|
16 | 8 | #####
|
17 | 9 | ##### Subsidence
|
18 | 10 | #####
|
19 | 11 |
|
20 |
| -subsidence!(ᶜρχₜ, ᶜρ, ᶠu³, ᶜχ, ::Val{:none}) = |
21 |
| - @. ᶜρχₜ -= ᶜρ * (ᶜsubdivᵥ(ᶠu³ * ᶠinterp(ᶜχ)) - ᶜχ * ᶜsubdivᵥ(ᶠu³)) |
22 |
| -subsidence!(ᶜρχₜ, ᶜρ, ᶠu³, ᶜχ, ::Val{:first_order}) = |
23 |
| - @. ᶜρχₜ -= ᶜρ * (ᶜsubdivᵥ(ᶠupwind1(ᶠu³, ᶜχ)) - ᶜχ * ᶜsubdivᵥ(ᶠu³)) |
24 |
| -subsidence!(ᶜρχₜ, ᶜρ, ᶠu³, ᶜχ, ::Val{:third_order}) = |
25 |
| - @. ᶜρχₜ -= ᶜρ * (ᶜsubdivᵥ(ᶠupwind3(ᶠu³, ᶜχ)) - ᶜχ * ᶜsubdivᵥ(ᶠu³)) |
26 |
| - |
27 |
| -function subsidence_tendency!(Yₜ, Y, p, t, ::Subsidence) |
28 |
| - (; moisture_model) = p.atmos |
29 |
| - subsidence_profile = p.atmos.subsidence.prof |
30 |
| - (; ᶜh_tot, ᶜspecific) = p.precomputed |
31 |
| - |
32 |
| - ᶠz = Fields.coordinate_field(axes(Y.f)).z |
33 |
| - ᶠlg = Fields.local_geometry_field(Y.f) |
34 |
| - ᶠsubsidence³ = p.scratch.ᶠtemp_CT3 |
35 |
| - @. ᶠsubsidence³ = |
36 |
| - subsidence_profile(ᶠz) * CT3(unit_basis_vector_data(CT3, ᶠlg)) |
37 |
| - |
38 |
| - # LS Subsidence |
39 |
| - subsidence!(Yₜ.c.ρe_tot, Y.c.ρ, ᶠsubsidence³, ᶜh_tot, Val{:first_order}()) |
40 |
| - subsidence!( |
41 |
| - Yₜ.c.ρq_tot, |
42 |
| - Y.c.ρ, |
43 |
| - ᶠsubsidence³, |
44 |
| - ᶜspecific.q_tot, |
45 |
| - Val{:first_order}(), |
46 |
| - ) |
47 |
| - if moisture_model isa NonEquilMoistModel |
48 |
| - subsidence!( |
49 |
| - Yₜ.c.ρq_liq, |
50 |
| - Y.c.ρ, |
51 |
| - ᶠsubsidence³, |
52 |
| - ᶜspecific.q_liq, |
53 |
| - Val{:first_order}(), |
54 |
| - ) |
55 |
| - subsidence!( |
56 |
| - Yₜ.c.ρq_ice, |
57 |
| - Y.c.ρ, |
58 |
| - ᶠsubsidence³, |
59 |
| - ᶜspecific.q_ice, |
60 |
| - Val{:first_order}(), |
61 |
| - ) |
| 12 | +subsidence_tracer(::Val{:h_tot}, thermo_params, ts, ρ, ρe_tot) = |
| 13 | + TD.total_specific_enthalpy(thermo_params, ts, ρe_tot / ρ) |
| 14 | +subsidence_tracer(::Val{:q_tot}, thermo_params, ts, ρ, ρe_tot) = |
| 15 | + TD.total_specific_humidity(thermo_params, ts) |
| 16 | +subsidence_tracer(::Val{:q_liq}, thermo_params, ts, ρ, ρe_tot) = |
| 17 | + TD.liquid_specific_humidity(thermo_params, ts) |
| 18 | +subsidence_tracer(::Val{:q_ice}, thermo_params, ts, ρ, ρe_tot) = |
| 19 | + TD.ice_specific_humidity(thermo_params, ts) |
| 20 | + |
| 21 | +function subsidence_tendency(χname, subsidence, thermo_params, ᶜts, ᶜρ, ᶜρe_tot) |
| 22 | + subsidence isa Nothing && return NullBroadcasted() |
| 23 | + ᶠspace = Spaces.face_space(axes(ᶜρ)) |
| 24 | + ᶠu³ = if subsidence isa Subsidence |
| 25 | + ᶠsubsidence³(ᶠspace, subsidence) |
| 26 | + else |
| 27 | + subsidence |
62 | 28 | end
|
| 29 | + ᶜχ = @. lazy(subsidence_tracer(χname, thermo_params, ᶜts, ᶜρ, ᶜρe_tot)) |
| 30 | + return subsidence_tendency(ᶜρ, ᶜχ, ᶠu³, Val(:first_order)) |
| 31 | +end |
63 | 32 |
|
64 |
| - return nothing |
| 33 | +function ᶠsubsidence³(ᶠspace, subsidence::Subsidence) |
| 34 | + ᶠz = Fields.coordinate_field(ᶠspace).z |
| 35 | + ᶠlg = Fields.local_geometry_field(ᶠspace) |
| 36 | + (; prof) = subsidence |
| 37 | + return @. lazy(prof(ᶠz) * CT3(unit_basis_vector_data(CT3, ᶠlg))) |
65 | 38 | end
|
| 39 | +subsidence_tendency(ᶜρ, ᶜχ, ᶠu³, ::Val{:none}) = |
| 40 | + @. lazy(- ᶜρ * (ᶜsubdivᵥ(ᶠu³ * ᶠinterp(ᶜχ)) - ᶜχ * ᶜsubdivᵥ(ᶠu³))) |
| 41 | +subsidence_tendency(ᶜρ, ᶜχ, ᶠu³, ::Val{:first_order}) = |
| 42 | + @. lazy(- ᶜρ * (ᶜsubdivᵥ(ᶠupwind1(ᶠu³, ᶜχ)) - ᶜχ * ᶜsubdivᵥ(ᶠu³))) |
| 43 | +subsidence_tendency(ᶜρ, ᶜχ, ᶠu³, ::Val{:third_order}) = |
| 44 | + @. lazy(- ᶜρ * (ᶜsubdivᵥ(ᶠupwind3(ᶠu³, ᶜχ)) - ᶜχ * ᶜsubdivᵥ(ᶠu³))) |
0 commit comments