Skip to content

Commit 1e0782c

Browse files
authored
Merge pull request #386 from pdziekan/sgs_length_profile
SGS_mixing_length as a profile
2 parents 1c430c7 + 5a3cc95 commit 1e0782c

File tree

12 files changed

+106
-180
lines changed

12 files changed

+106
-180
lines changed

bindings/python/lgrngn.hpp

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -345,6 +345,26 @@ namespace libcloudphxx
345345
{
346346
throw std::runtime_error("w_LS profile does not feature a getter yet - TODO");
347347
}
348+
349+
template <typename real_t>
350+
void set_SGS_mix_len(
351+
lgr::opts_init_t<real_t> *arg,
352+
const bp_array &vec
353+
)
354+
{
355+
sanity_checks(vec);
356+
arg->SGS_mix_len.resize(0);
357+
for (int i = 0; i < len(vec); ++i)
358+
arg->SGS_mix_len.push_back(bp::extract<real_t>(vec[i]));
359+
}
360+
361+
template <typename real_t>
362+
bp_array get_SGS_mix_len(
363+
lgr::opts_init_t<real_t> *arg
364+
)
365+
{
366+
throw std::runtime_error("SGS_mix_len profile does not feature a getter yet - TODO");
367+
}
348368
};
349369
};
350370
};

bindings/python/lib.cpp

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -214,10 +214,6 @@ BOOST_PYTHON_MODULE(libcloudphxx)
214214
.value("beard77fast", lgr::vt_t::beard77fast)
215215
.value("khvorostyanov_spherical", lgr::vt_t::khvorostyanov_spherical)
216216
.value("khvorostyanov_nonspherical", lgr::vt_t::khvorostyanov_nonspherical);
217-
bp::enum_<lgr::SGS_length_scale_t::SGS_length_scale_t>("SGS_length_scale_t")
218-
.value("vertical", lgr::SGS_length_scale_t::vertical)
219-
.value("arithmetic_mean", lgr::SGS_length_scale_t::arithmetic_mean)
220-
.value("geometric_mean", lgr::SGS_length_scale_t::geometric_mean);
221217
bp::enum_<lgr::RH_formula_t::RH_formula_t>("RH_formula_t")
222218
.value("pv_cc", lgr::RH_formula_t::pv_cc)
223219
.value("rv_cc", lgr::RH_formula_t::rv_cc)
@@ -296,12 +292,12 @@ BOOST_PYTHON_MODULE(libcloudphxx)
296292
.def_readwrite("src_sd_conc", &lgr::opts_init_t<real_t>::src_sd_conc)
297293
.def_readwrite("n_sd_max", &lgr::opts_init_t<real_t>::n_sd_max)
298294
.def_readwrite("terminal_velocity", &lgr::opts_init_t<real_t>::terminal_velocity)
299-
.def_readwrite("SGS_length_scale", &lgr::opts_init_t<real_t>::SGS_length_scale)
300295
.def_readwrite("RH_formula", &lgr::opts_init_t<real_t>::RH_formula)
301296
.def_readwrite("chem_rho", &lgr::opts_init_t<real_t>::chem_rho)
302297
.def_readwrite("RH_max", &lgr::opts_init_t<real_t>::RH_max)
303298
.def_readwrite("rng_seed", &lgr::opts_init_t<real_t>::rng_seed)
304299
.add_property("w_LS", &lgrngn::get_w_LS<real_t>, &lgrngn::set_w_LS<real_t>)
300+
.add_property("SGS_mix_len", &lgrngn::get_SGS_mix_len<real_t>, &lgrngn::set_SGS_mix_len<real_t>)
305301
.add_property("kernel_parameters", &lgrngn::get_kp<real_t>, &lgrngn::set_kp<real_t>)
306302
;
307303
bp::class_<lgr::particles_proto_t<real_t>/*, boost::noncopyable*/>("particles_proto_t")

include/libcloudph++/lgrngn/SGS_length_scale.hpp

Lines changed: 0 additions & 14 deletions
This file was deleted.

include/libcloudph++/lgrngn/opts_init.hpp

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,6 @@
1010
#include "extincl.hpp"
1111
#include "kernel.hpp"
1212
#include "terminal_velocity.hpp"
13-
#include "SGS_length_scale.hpp"
1413
#include "advection_scheme.hpp"
1514
#include "RH_formula.hpp"
1615
#include "../common/chem.hpp"
@@ -88,9 +87,6 @@ namespace libcloudphxx
8887
// terminal velocity formula
8988
vt_t::vt_t terminal_velocity;
9089

91-
// SGS mixing length
92-
SGS_length_scale_t::SGS_length_scale_t SGS_length_scale;
93-
9490
// super-droplet advection scheme
9591
as_t::as_t adve_scheme;
9692

@@ -130,6 +126,9 @@ namespace libcloudphxx
130126
// subsidence rate profile, positive downwards [m/s]
131127
std::vector<real_t> w_LS;
132128

129+
// SGS mixing length profile [m]
130+
std::vector<real_t> SGS_mix_len;
131+
133132
real_t rd_min; // minimal dry radius of droplets (works only for init from spectrum)
134133

135134
// ctor with defaults (C++03 compliant) ...
@@ -158,7 +157,6 @@ namespace libcloudphxx
158157
chem_rho(0), // dry particle density //TODO add checking if the user gave a different value (np w init) (was 1.8e-3)
159158
rng_seed(44),
160159
terminal_velocity(vt_t::undefined),
161-
SGS_length_scale(SGS_length_scale_t::geometric_mean),
162160
kernel(kernel_t::undefined),
163161
adve_scheme(as_t::implicit),
164162
RH_formula(RH_formula_t::pv_cc),

src/impl/particles_impl.ipp

Lines changed: 2 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,6 @@
1414
#include <boost/numeric/odeint/external/thrust/thrust_operations.hpp>
1515
#include <boost/numeric/odeint/external/thrust/thrust_resize.hpp>
1616

17-
#include <libcloudph++/common/SGS_length_scale.hpp>
18-
1917
#include <map>
2018

2119
namespace libcloudphxx
@@ -150,9 +148,8 @@ namespace libcloudphxx
150148
eta,// dynamic viscosity
151149
diss_rate; // turbulent kinetic energy dissipation rate
152150

153-
real_t lambda;
154-
155151
thrust_device::vector<real_t> w_LS; // large-scale subsidence velocity profile
152+
thrust_device::vector<real_t> SGS_mix_len; // SGS mixing length profile
156153

157154
// sorting needed only for diagnostics and coalescence
158155
bool sorted;
@@ -293,6 +290,7 @@ namespace libcloudphxx
293290
halo_size * (opts_init.nz + 1) * opts_init.ny // 3D
294291
),
295292
w_LS(opts_init.w_LS),
293+
SGS_mix_len(opts_init.SGS_mix_len),
296294
adve_scheme(opts_init.adve_scheme),
297295
pure_const_multi (((opts_init.sd_conc) == 0) && (opts_init.sd_const_multi > 0 || opts_init.dry_sizes.size() > 0)) // coal prob can be greater than one only in sd_conc simulations
298296
{
@@ -311,29 +309,6 @@ namespace libcloudphxx
311309
#endif
312310
*increase_sstp_coal = false;
313311

314-
switch (opts_init.SGS_length_scale)
315-
{
316-
case SGS_length_scale_t::vertical:
317-
lambda =
318-
n_dims == 1 ? common::SGS_length_scale::vertical(opts_init.dx * si::metres) / si::metres: // 1D
319-
n_dims == 2 ? common::SGS_length_scale::vertical(opts_init.dx * si::metres, opts_init.dz * si::metres) / si::metres: // 2D
320-
common::SGS_length_scale::vertical(opts_init.dx * si::metres, opts_init.dy * si::metres, opts_init.dz * si::metres)/ si::metres; // 3D
321-
break;
322-
case SGS_length_scale_t::arithmetic_mean:
323-
lambda =
324-
n_dims == 1 ? common::SGS_length_scale::arithmetic_mean(opts_init.dx * si::metres) / si::metres: // 1D
325-
n_dims == 2 ? common::SGS_length_scale::arithmetic_mean(opts_init.dx * si::metres, opts_init.dz * si::metres) / si::metres: // 2D
326-
common::SGS_length_scale::arithmetic_mean(opts_init.dx * si::metres, opts_init.dy * si::metres, opts_init.dz * si::metres)/ si::metres; // 3D
327-
break;
328-
case SGS_length_scale_t::geometric_mean:
329-
lambda =
330-
n_dims == 1 ? common::SGS_length_scale::geometric_mean(opts_init.dx * si::metres) / si::metres: // 1D
331-
n_dims == 2 ? common::SGS_length_scale::geometric_mean(opts_init.dx * si::metres, opts_init.dz * si::metres) / si::metres: // 2D
332-
common::SGS_length_scale::geometric_mean(opts_init.dx * si::metres, opts_init.dy * si::metres, opts_init.dz * si::metres)/ si::metres; // 3D
333-
break;
334-
default: assert(false && "unrecognized value of opts_init.SGS_length_scale");
335-
}
336-
337312
// initialising host temporary arrays
338313
{
339314
thrust_size_t n_grid;

src/impl/particles_impl_hskpng_tke.ipp

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,24 +16,32 @@ namespace libcloudphxx
1616
template<class real_t>
1717
struct common__turbulence__tke
1818
{
19-
const quantity<si::length, real_t> lambda;
20-
common__turbulence__tke(const real_t &lambda):
21-
lambda(lambda * si::metres){}
22-
2319
BOOST_GPU_ENABLED
24-
real_t operator()(const real_t &diss_rate)
20+
real_t operator()(const real_t &diss_rate, const real_t &lambda)
2521
{
22+
assert(lambda > 0);
2623
return common::GA17_turbulence::tke(
2724
diss_rate * si::metres * si::metres / si::seconds / si::seconds / si::seconds,
28-
lambda) / si::metres / si::metres * si::seconds * si::seconds;
25+
lambda * si::metres) / si::metres / si::metres * si::seconds * si::seconds;
2926
}
3027
};
3128
};
3229
// calc the SGS TKE, in place of dissipation rate
3330
template <typename real_t, backend_t device>
3431
void particles_t<real_t, device>::impl::hskpng_tke()
3532
{
36-
thrust::transform(diss_rate.begin(), diss_rate.end(), diss_rate.begin(), detail::common__turbulence__tke<real_t>(lambda));
33+
namespace arg = thrust::placeholders;
34+
35+
thrust::transform(
36+
diss_rate.begin(), diss_rate.end(),
37+
thrust::make_permutation_iterator(SGS_mix_len.begin(), // profile of the SGS mixing length
38+
thrust::make_transform_iterator( // calculate vertical index from cell index
39+
thrust::make_counting_iterator<thrust_size_t>(0),
40+
arg::_1 % opts_init.nz
41+
)
42+
),
43+
diss_rate.begin(),
44+
detail::common__turbulence__tke<real_t>());
3745
}
3846
};
3947
};

src/impl/particles_impl_hskpng_turb_vel.ipp

Lines changed: 16 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,16 +16,13 @@ namespace libcloudphxx
1616
template<class real_t>
1717
struct common__turbulence__tau
1818
{
19-
const quantity<si::length, real_t> lambda;
20-
common__turbulence__tau(const real_t &lambda):
21-
lambda(lambda * si::metres){}
22-
2319
BOOST_GPU_ENABLED
24-
real_t operator()(const real_t &tke)
20+
real_t operator()(const real_t &tke, const real_t &lambda)
2521
{
22+
assert(lambda > 0);
2623
return common::GA17_turbulence::tau(
2724
tke * si::metres * si::metres / si::seconds / si::seconds,
28-
lambda) / si::seconds;
25+
lambda * si::metres) / si::seconds;
2926
}
3027
};
3128

@@ -54,9 +51,21 @@ namespace libcloudphxx
5451
template <typename real_t, backend_t device>
5552
void particles_t<real_t, device>::impl::hskpng_turb_vel(const bool only_vertical)
5653
{
54+
namespace arg = thrust::placeholders;
55+
5756
thrust_device::vector<real_t> &tau(tmp_device_real_cell);
5857
thrust_device::vector<real_t> &tke(diss_rate); // should be called after hskpng_tke, which replaces diss_rate with tke
59-
thrust::transform(tke.begin(), tke.end(), tau.begin(), detail::common__turbulence__tau<real_t>(lambda));
58+
59+
thrust::transform(tke.begin(), tke.end(),
60+
thrust::make_permutation_iterator(SGS_mix_len.begin(), // profile of the SGS mixing length
61+
thrust::make_transform_iterator( // calculate vertical index from cell index
62+
thrust::make_counting_iterator<thrust_size_t>(0),
63+
arg::_1 % opts_init.nz
64+
)
65+
),
66+
tau.begin(),
67+
detail::common__turbulence__tau<real_t>()
68+
);
6069

6170
thrust_device::vector<real_t> &r_normal(tmp_device_real_part);
6271
thrust_device::vector<real_t> * vel_turbs_vctrs_a[] = {&up, &wp, &vp};

src/impl/particles_impl_init_sanity_check.ipp

Lines changed: 41 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -74,39 +74,47 @@ namespace libcloudphxx
7474
if(opts_init.sd_const_multi > 0 && opts_init.src_switch)
7575
throw std::runtime_error("aerosol source and constant multiplicity option are not compatible");
7676

77-
if (n_dims > 0)
78-
{
79-
if (!(opts_init.x0 >= 0 && opts_init.x0 < m1(opts_init.nx) * opts_init.dx))
80-
throw std::runtime_error("!(x0 >= 0 & x0 < min(1,nx)*dz)");
81-
if (!(opts_init.y0 >= 0 && opts_init.y0 < m1(opts_init.ny) * opts_init.dy))
82-
throw std::runtime_error("!(y0 >= 0 & y0 < min(1,ny)*dy)");
83-
if (!(opts_init.z0 >= 0 && opts_init.z0 < m1(opts_init.nz) * opts_init.dz))
84-
throw std::runtime_error("!(z0 >= 0 & z0 < min(1,nz)*dz)");
85-
// check temporarily disabled since dewv_id is not passed anymore, TODO: fix it
86-
// if (!(opts_init.x1 > opts_init.x0 && opts_init.x1 <= m1(opts_init.nx) * opts_init.dx) && dev_id == -1) // only for single device runs, since on multi_CUDA x1 is not yet adjusted to local domain
87-
// throw std::runtime_error("!(x1 > x0 & x1 <= min(1,nx)*dx)");
88-
if (!(opts_init.y1 > opts_init.y0 && opts_init.y1 <= m1(opts_init.ny) * opts_init.dy))
89-
throw std::runtime_error("!(y1 > y0 & y1 <= min(1,ny)*dy)");
90-
if (!(opts_init.z1 > opts_init.z0 && opts_init.z1 <= m1(opts_init.nz) * opts_init.dz))
91-
throw std::runtime_error("!(z1 > z0 & z1 <= min(1,nz)*dz)");
92-
}
93-
94-
if (opts_init.dt == 0) throw std::runtime_error("please specify opts_init.dt");
95-
if (opts_init.sd_conc * opts_init.sd_const_multi != 0) throw std::runtime_error("specify either opts_init.sd_conc or opts_init.sd_const_multi, not both");
96-
if (opts_init.sd_conc == 0 && opts_init.sd_const_multi == 0 && opts_init.dry_sizes.size() == 0) throw std::runtime_error("please specify opts_init.sd_conc, opts_init.sd_const_multi or opts_init.dry_sizes");
97-
if (opts_init.coal_switch)
98-
{
99-
if(opts_init.terminal_velocity == vt_t::undefined) throw std::runtime_error("please specify opts_init.terminal_velocity or turn off opts_init.coal_switch");
100-
if(opts_init.kernel == kernel_t::undefined) throw std::runtime_error("please specify opts_init.kernel");
101-
}
102-
if (opts_init.sedi_switch)
103-
if(opts_init.terminal_velocity == vt_t::undefined) throw std::runtime_error("please specify opts_init.terminal_velocity or turn off opts_init.sedi_switch");
104-
if (opts_init.sedi_switch && opts_init.nz == 0)
105-
throw std::runtime_error("opts_init.sedi_switch can be True only if n_dims > 1");
106-
if (opts_init.subs_switch && opts_init.nz == 0)
107-
throw std::runtime_error("opts_init.subs_switch can be True only if n_dims > 1");
108-
if (opts_init.subs_switch && opts_init.nz != w_LS.size())
109-
throw std::runtime_error("opts_init.subs_switch == True, but subsidence velocity profile size != nz");
77+
if (n_dims > 0)
78+
{
79+
if (!(opts_init.x0 >= 0 && opts_init.x0 < m1(opts_init.nx) * opts_init.dx))
80+
throw std::runtime_error("!(x0 >= 0 & x0 < min(1,nx)*dz)");
81+
if (!(opts_init.y0 >= 0 && opts_init.y0 < m1(opts_init.ny) * opts_init.dy))
82+
throw std::runtime_error("!(y0 >= 0 & y0 < min(1,ny)*dy)");
83+
if (!(opts_init.z0 >= 0 && opts_init.z0 < m1(opts_init.nz) * opts_init.dz))
84+
throw std::runtime_error("!(z0 >= 0 & z0 < min(1,nz)*dz)");
85+
// check temporarily disabled since dewv_id is not passed anymore, TODO: fix it
86+
// if (!(opts_init.x1 > opts_init.x0 && opts_init.x1 <= m1(opts_init.nx) * opts_init.dx) && dev_id == -1) // only for single device runs, since on multi_CUDA x1 is not yet adjusted to local domain
87+
// throw std::runtime_error("!(x1 > x0 & x1 <= min(1,nx)*dx)");
88+
if (!(opts_init.y1 > opts_init.y0 && opts_init.y1 <= m1(opts_init.ny) * opts_init.dy))
89+
throw std::runtime_error("!(y1 > y0 & y1 <= min(1,ny)*dy)");
90+
if (!(opts_init.z1 > opts_init.z0 && opts_init.z1 <= m1(opts_init.nz) * opts_init.dz))
91+
throw std::runtime_error("!(z1 > z0 & z1 <= min(1,nz)*dz)");
92+
}
93+
94+
if (opts_init.dt == 0) throw std::runtime_error("please specify opts_init.dt");
95+
if (opts_init.sd_conc * opts_init.sd_const_multi != 0) throw std::runtime_error("specify either opts_init.sd_conc or opts_init.sd_const_multi, not both");
96+
if (opts_init.sd_conc == 0 && opts_init.sd_const_multi == 0 && opts_init.dry_sizes.size() == 0) throw std::runtime_error("please specify opts_init.sd_conc, opts_init.sd_const_multi or opts_init.dry_sizes");
97+
if (opts_init.coal_switch)
98+
{
99+
if(opts_init.terminal_velocity == vt_t::undefined) throw std::runtime_error("please specify opts_init.terminal_velocity or turn off opts_init.coal_switch");
100+
if(opts_init.kernel == kernel_t::undefined) throw std::runtime_error("please specify opts_init.kernel");
101+
}
102+
if (opts_init.sedi_switch)
103+
if(opts_init.terminal_velocity == vt_t::undefined) throw std::runtime_error("please specify opts_init.terminal_velocity or turn off opts_init.sedi_switch");
104+
if (opts_init.sedi_switch && opts_init.nz == 0)
105+
throw std::runtime_error("opts_init.sedi_switch can be True only if n_dims > 1");
106+
if (opts_init.subs_switch && opts_init.nz == 0)
107+
throw std::runtime_error("opts_init.subs_switch can be True only if n_dims > 1");
108+
if (opts_init.turb_adve_switch && opts_init.nz == 0)
109+
throw std::runtime_error("opts_init.turb_adve_switch can be True only if n_dims > 1");
110+
if (opts_init.turb_cond_switch && opts_init.nz == 0)
111+
throw std::runtime_error("opts_init.turb_cond_switch can be True only if n_dims > 1");
112+
if (opts_init.subs_switch && opts_init.nz != w_LS.size())
113+
throw std::runtime_error("opts_init.subs_switch == True, but subsidence velocity profile size != nz");
114+
if ((opts_init.turb_adve_switch || opts_init.turb_cond_switch) && opts_init.nz != SGS_mix_len.size())
115+
throw std::runtime_error("at least one of opts_init.turb_adve_switch, opts_init.turb_cond_switch is true, but SGS mixing length profile size != nz");
116+
if(opts_init.SGS_mix_len.size() > 0 && *std::min(opts_init.SGS_mix_len.begin(), opts_init.SGS_mix_len.end()) <= 0)
117+
throw std::runtime_error("SGS_mix_len <= 0");
110118
}
111119
};
112120
};

tests/python/unit/CMakeLists.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
# non-pytest tests
2-
foreach(test api_blk_1m api_blk_2m api_lgrngn api_common segfault_20150216 col_kernels terminal_velocities SGS_length_scales SD_removal uniform_init source chem_coal sstp_cond multiple_kappas adve_scheme lgrngn_subsidence sat_adj_blk_1m )
2+
foreach(test api_blk_1m api_blk_2m api_lgrngn api_common segfault_20150216 col_kernels terminal_velocities SD_removal uniform_init source chem_coal sstp_cond multiple_kappas adve_scheme lgrngn_subsidence sat_adj_blk_1m )
33
#TODO: indicate that tests depend on the lib
44
add_test(
55
NAME ${test}

tests/python/unit/SGS_length_scales.py

Lines changed: 0 additions & 54 deletions
This file was deleted.

0 commit comments

Comments
 (0)