PySDM_examples.Abade_and_Albuquerque_2024.simulation
1import numpy as np 2 3from PySDM_examples.utils import BasicSimulation 4 5from PySDM.particulator import Particulator 6from PySDM.dynamics import ( 7 Condensation, 8 AmbientThermodynamics, 9 VapourDepositionOnIce, 10 Freezing, 11) 12from PySDM.initialisation.sampling.spectral_sampling import ConstantMultiplicity 13from PySDM.products import ( 14 AmbientTemperature, 15 AmbientWaterVapourMixingRatio, 16 ParcelDisplacement, 17 WaterMixingRatio, 18 SpecificIceWaterContent, 19) 20from PySDM.environments import Parcel 21 22 23class Simulation(BasicSimulation): 24 def __init__(self, settings): 25 26 dynamics = [ 27 AmbientThermodynamics(), 28 Condensation(), 29 ] 30 31 if settings.enable_immersion_freezing: 32 dynamics.append( 33 Freezing( 34 immersion_freezing=( 35 "singular" if settings.singular else "time-dependent" 36 ) 37 ) 38 ) 39 40 if settings.enable_vapour_deposition_on_ice: 41 dynamics.append(VapourDepositionOnIce(adaptive=True)) 42 43 environment = Parcel( 44 dt=settings.timestep, 45 mass_of_dry_air=settings.mass_of_dry_air, 46 p0=settings.initial_total_pressure, 47 initial_water_vapour_mixing_ratio=settings.initial_water_vapour_mixing_ratio, 48 T0=settings.initial_temperature, 49 w=settings.updraft, 50 mixed_phase=True, 51 backend=settings.backend, 52 ) 53 r_dry, n_in_dv = ConstantMultiplicity( 54 settings.soluble_aerosol 55 ).sample_deterministic(n_sd=settings.n_sd) 56 attributes = environment.init_attributes( 57 n_in_dv=n_in_dv, 58 kappa=settings.kappa, 59 r_dry=r_dry, 60 ) 61 attributes["signed water mass"] = ( 62 settings.backend.formulae.particle_shape_and_density.volume_to_mass( 63 attributes["volume"] 64 ) 65 ) 66 del attributes["volume"] 67 68 if settings.enable_immersion_freezing: 69 trivia = settings.backend.formulae.trivia 70 n_inp = int(settings.n_sd * settings.freezing_inp_frac) 71 72 rng = np.random.default_rng(seed=settings.backend.formulae.seed) 73 insoluble_surface_area = trivia.sphere_surface( 74 diameter=2 * settings.freezing_inp_dry_radius 75 ) 76 attributes[ 77 "freezing temperature" if settings.singular else "immersed surface area" 78 ] = rng.permutation( 79 np.pad( 80 ( 81 settings.backend.formulae.freezing_temperature_spectrum.invcdf( 82 cdf=rng.uniform(low=0, high=1, size=n_inp), 83 A_insol=insoluble_surface_area, 84 ) 85 if settings.singular 86 else np.full(n_inp, insoluble_surface_area) 87 ), 88 (0, settings.n_sd - n_inp), 89 mode="constant", 90 constant_values=( 91 settings.backend.formulae.constants.HOMOGENEOUS_FREEZING_THRESHOLD 92 if settings.singular 93 else 0 94 ), 95 ) 96 ) 97 98 self.products = ( 99 WaterMixingRatio(name="water", radius_range=(0, np.inf)), 100 SpecificIceWaterContent(name="ice"), 101 ParcelDisplacement(name="height"), 102 AmbientTemperature(name="T"), 103 AmbientWaterVapourMixingRatio( 104 name="vapour", var="water_vapour_mixing_ratio" 105 ), 106 ) 107 particulator = Particulator( 108 n_sd=settings.n_sd, 109 environment=environment, 110 dynamics=dynamics, 111 attributes=attributes, 112 products=self.products, 113 ) 114 super().__init__(particulator=particulator) 115 116 def run(self, *, nt, steps_per_output_interval): 117 return self._run(nt=nt, steps_per_output_interval=steps_per_output_interval)
24class Simulation(BasicSimulation): 25 def __init__(self, settings): 26 27 dynamics = [ 28 AmbientThermodynamics(), 29 Condensation(), 30 ] 31 32 if settings.enable_immersion_freezing: 33 dynamics.append( 34 Freezing( 35 immersion_freezing=( 36 "singular" if settings.singular else "time-dependent" 37 ) 38 ) 39 ) 40 41 if settings.enable_vapour_deposition_on_ice: 42 dynamics.append(VapourDepositionOnIce(adaptive=True)) 43 44 environment = Parcel( 45 dt=settings.timestep, 46 mass_of_dry_air=settings.mass_of_dry_air, 47 p0=settings.initial_total_pressure, 48 initial_water_vapour_mixing_ratio=settings.initial_water_vapour_mixing_ratio, 49 T0=settings.initial_temperature, 50 w=settings.updraft, 51 mixed_phase=True, 52 backend=settings.backend, 53 ) 54 r_dry, n_in_dv = ConstantMultiplicity( 55 settings.soluble_aerosol 56 ).sample_deterministic(n_sd=settings.n_sd) 57 attributes = environment.init_attributes( 58 n_in_dv=n_in_dv, 59 kappa=settings.kappa, 60 r_dry=r_dry, 61 ) 62 attributes["signed water mass"] = ( 63 settings.backend.formulae.particle_shape_and_density.volume_to_mass( 64 attributes["volume"] 65 ) 66 ) 67 del attributes["volume"] 68 69 if settings.enable_immersion_freezing: 70 trivia = settings.backend.formulae.trivia 71 n_inp = int(settings.n_sd * settings.freezing_inp_frac) 72 73 rng = np.random.default_rng(seed=settings.backend.formulae.seed) 74 insoluble_surface_area = trivia.sphere_surface( 75 diameter=2 * settings.freezing_inp_dry_radius 76 ) 77 attributes[ 78 "freezing temperature" if settings.singular else "immersed surface area" 79 ] = rng.permutation( 80 np.pad( 81 ( 82 settings.backend.formulae.freezing_temperature_spectrum.invcdf( 83 cdf=rng.uniform(low=0, high=1, size=n_inp), 84 A_insol=insoluble_surface_area, 85 ) 86 if settings.singular 87 else np.full(n_inp, insoluble_surface_area) 88 ), 89 (0, settings.n_sd - n_inp), 90 mode="constant", 91 constant_values=( 92 settings.backend.formulae.constants.HOMOGENEOUS_FREEZING_THRESHOLD 93 if settings.singular 94 else 0 95 ), 96 ) 97 ) 98 99 self.products = ( 100 WaterMixingRatio(name="water", radius_range=(0, np.inf)), 101 SpecificIceWaterContent(name="ice"), 102 ParcelDisplacement(name="height"), 103 AmbientTemperature(name="T"), 104 AmbientWaterVapourMixingRatio( 105 name="vapour", var="water_vapour_mixing_ratio" 106 ), 107 ) 108 particulator = Particulator( 109 n_sd=settings.n_sd, 110 environment=environment, 111 dynamics=dynamics, 112 attributes=attributes, 113 products=self.products, 114 ) 115 super().__init__(particulator=particulator) 116 117 def run(self, *, nt, steps_per_output_interval): 118 return self._run(nt=nt, steps_per_output_interval=steps_per_output_interval)
Simulation(settings)
25 def __init__(self, settings): 26 27 dynamics = [ 28 AmbientThermodynamics(), 29 Condensation(), 30 ] 31 32 if settings.enable_immersion_freezing: 33 dynamics.append( 34 Freezing( 35 immersion_freezing=( 36 "singular" if settings.singular else "time-dependent" 37 ) 38 ) 39 ) 40 41 if settings.enable_vapour_deposition_on_ice: 42 dynamics.append(VapourDepositionOnIce(adaptive=True)) 43 44 environment = Parcel( 45 dt=settings.timestep, 46 mass_of_dry_air=settings.mass_of_dry_air, 47 p0=settings.initial_total_pressure, 48 initial_water_vapour_mixing_ratio=settings.initial_water_vapour_mixing_ratio, 49 T0=settings.initial_temperature, 50 w=settings.updraft, 51 mixed_phase=True, 52 backend=settings.backend, 53 ) 54 r_dry, n_in_dv = ConstantMultiplicity( 55 settings.soluble_aerosol 56 ).sample_deterministic(n_sd=settings.n_sd) 57 attributes = environment.init_attributes( 58 n_in_dv=n_in_dv, 59 kappa=settings.kappa, 60 r_dry=r_dry, 61 ) 62 attributes["signed water mass"] = ( 63 settings.backend.formulae.particle_shape_and_density.volume_to_mass( 64 attributes["volume"] 65 ) 66 ) 67 del attributes["volume"] 68 69 if settings.enable_immersion_freezing: 70 trivia = settings.backend.formulae.trivia 71 n_inp = int(settings.n_sd * settings.freezing_inp_frac) 72 73 rng = np.random.default_rng(seed=settings.backend.formulae.seed) 74 insoluble_surface_area = trivia.sphere_surface( 75 diameter=2 * settings.freezing_inp_dry_radius 76 ) 77 attributes[ 78 "freezing temperature" if settings.singular else "immersed surface area" 79 ] = rng.permutation( 80 np.pad( 81 ( 82 settings.backend.formulae.freezing_temperature_spectrum.invcdf( 83 cdf=rng.uniform(low=0, high=1, size=n_inp), 84 A_insol=insoluble_surface_area, 85 ) 86 if settings.singular 87 else np.full(n_inp, insoluble_surface_area) 88 ), 89 (0, settings.n_sd - n_inp), 90 mode="constant", 91 constant_values=( 92 settings.backend.formulae.constants.HOMOGENEOUS_FREEZING_THRESHOLD 93 if settings.singular 94 else 0 95 ), 96 ) 97 ) 98 99 self.products = ( 100 WaterMixingRatio(name="water", radius_range=(0, np.inf)), 101 SpecificIceWaterContent(name="ice"), 102 ParcelDisplacement(name="height"), 103 AmbientTemperature(name="T"), 104 AmbientWaterVapourMixingRatio( 105 name="vapour", var="water_vapour_mixing_ratio" 106 ), 107 ) 108 particulator = Particulator( 109 n_sd=settings.n_sd, 110 environment=environment, 111 dynamics=dynamics, 112 attributes=attributes, 113 products=self.products, 114 ) 115 super().__init__(particulator=particulator)