@@ -217,28 +217,29 @@ function get_thresholds_ρ_g(params::CMP.ParametersP3, F_rim, ρ_rim)
217
217
return (; D_th, D_gr, D_cr, ρ_g)
218
218
end
219
219
220
+ function get_bounded_thresholds (state:: P3State , D_min = 0 , D_max = Inf )
221
+ FT = eltype (state)
222
+ (; D_th, D_gr, D_cr) = get_thresholds_ρ_g (state)
223
+ return clamp .((FT (D_min), D_th, D_gr, D_cr, FT (D_max)), FT (D_min), FT (D_max))
224
+ end
225
+
220
226
"""
221
227
get_segments(state::P3State)
222
228
223
- Return the segments of the size distribution.
229
+ Return the segments of the size distribution as a tuple of intervals .
224
230
225
231
# Arguments
226
232
- `state`: [`P3State`](@ref) object
227
233
228
234
# Returns
229
235
- `segments`: tuple of tuples, each containing the lower and upper bounds of a segment
230
236
231
- For example, if the (valid) thresholds are `(D_th, D_gr, D_cr)`, then the segments are:
237
+ For example, if the thresholds are `(D_th, D_gr, D_cr)`, then the segments are:
232
238
- `(0, D_th)`, `(D_th, D_gr)`, `(D_gr, D_cr)`, `(D_cr, Inf)`
233
239
"""
234
- function get_segments (state:: P3State )
235
- FT = eltype (state)
236
- (; D_th, D_gr, D_cr) = get_thresholds_ρ_g (state)
237
- # For certain high rimed values, D_gr < D_th (cf test/p3_tests.jl):
238
- # so here we filter away invalid thresholds
239
- # (this also works correctly for the unrimed case, where D_gr = D_cr = NaN)
240
- valid_D = filter (≥ (D_th), (D_th, D_gr, D_cr))
241
- segments = tuple .((FT (0 ), valid_D... ), (valid_D... , FT (Inf )))
240
+ function get_segments (state:: P3State , D_min = 0 , D_max = Inf )
241
+ thresholds = get_bounded_thresholds (state, D_min, D_max)
242
+ segments = tuple .(Base. front (thresholds), Base. tail (thresholds))
242
243
return segments
243
244
end
244
245
@@ -300,9 +301,9 @@ Return the mass of a particle based on where it falls in the particle-size-based
300
301
- `params, F_rim, ρ_rim`: The [`CMP.ParametersP3`](@ref), rime mass fraction, and rime density,
301
302
- `D`: maximum particle dimension [m]
302
303
"""
303
- function ice_mass (args_D ... )
304
- D = last (args_D )
305
- (a, b) = ice_mass_coeffs (args_D ... )
304
+ ice_mass ((; params, F_rim, ρ_rim) :: P3State , D) = ice_mass (params, F_rim, ρ_rim, D )
305
+ function ice_mass (params :: CMP.ParametersP3 , F_rim, ρ_rim, D )
306
+ (a, b) = ice_mass_coeffs (params, F_rim, ρ_rim, D )
306
307
return a * D^ b
307
308
end
308
309
@@ -322,13 +323,14 @@ Return the density of a particle at diameter D
322
323
by the volume of a sphere with the same D [MorrisonMilbrandt2015](@cite).
323
324
Needed for aspect ratio calculation, so we assume zero liquid fraction.
324
325
"""
325
- function ice_density (args_D ... )
326
- D = last (args_D )
327
- return ice_mass (args_D ... ) / CO. volume_sphere_D (D)
326
+ ice_density ((; params, F_rim, ρ_rim) :: P3State , D) = ice_density (params, F_rim, ρ_rim, D )
327
+ function ice_density (params :: CMP.ParametersP3 , F_rim, ρ_rim, D )
328
+ return ice_mass (params, F_rim, ρ_rim, D ) / CO. volume_sphere_D (D)
328
329
end
329
330
330
- function get_∂mass_∂D_coeffs (args_D... )
331
- (a, b) = ice_mass_coeffs (args_D... )
331
+ get_∂mass_∂D_coeffs ((; params, F_rim, ρ_rim):: P3State , D) = get_∂mass_∂D_coeffs (params, F_rim, ρ_rim, D)
332
+ function get_∂mass_∂D_coeffs (params:: CMP.ParametersP3 , F_rim, ρ_rim, D)
333
+ (a, b) = ice_mass_coeffs (params, F_rim, ρ_rim, D)
332
334
return a * b, b - 1
333
335
end
334
336
338
340
339
341
Return the derivative of the ice mass with respect to the particle diameter.
340
342
"""
341
- function ∂ice_mass_∂D (args_D ... )
342
- D = last (args_D )
343
- (a, b) = get_∂mass_∂D_coeffs (args_D ... )
343
+ ∂ice_mass_∂D ((; params, F_rim, ρ_rim) :: P3State , D) = ∂ice_mass_∂D (params, F_rim, ρ_rim, D )
344
+ function ∂ice_mass_∂D (params :: CMP.ParametersP3 , F_rim, ρ_rim, D )
345
+ (a, b) = get_∂mass_∂D_coeffs (params, F_rim, ρ_rim, D )
344
346
return a * D^ b
345
347
end
346
348
@@ -391,18 +393,18 @@ Returns the aspect ratio (ϕ) for an ice particle
391
393
divided by the volume of a spherical particle with the same D_max [MorrisonMilbrandt2015](@cite).
392
394
Assuming zero liquid fraction and oblate shape.
393
395
"""
394
- function ϕᵢ (args_D ... )
395
- D = last (args_D )
396
+ ϕᵢ ((; params, F_rim, ρ_rim) :: P3State , D) = ϕᵢ (params, F_rim, ρ_rim, D )
397
+ function ϕᵢ (params :: CMP.ParametersP3 , F_rim, ρ_rim, D )
396
398
FT = eltype (D)
397
- mᵢ = ice_mass (args_D ... )
398
- aᵢ = ice_area (args_D ... )
399
- ρᵢ = ice_density (args_D ... )
399
+ mᵢ = ice_mass (params, F_rim, ρ_rim, D )
400
+ aᵢ = ice_area (params, F_rim, ρ_rim, D )
401
+ ρᵢ = ice_density (params, F_rim, ρ_rim, D )
400
402
401
403
# TODO - prolate or oblate?
402
404
ϕ_ob = min (1 , 3 * sqrt (FT (π)) * mᵢ / (4 * ρᵢ * aᵢ^ FT (1.5 ))) # κ = 1/3
403
405
# ϕ_pr = max(1, 16 * ρᵢ^2 * aᵢ^3 / (9 * FT(π) * mᵢ^2)) # κ = -1/6
404
406
405
- return ifelse (D == 0 , 0 , ϕ_ob)
407
+ return ifelse (D == 0 , FT ( 0 ) , ϕ_ob)
406
408
end
407
409
408
410
# ## ----------------- ###
0 commit comments