def test_adiab_path(save_file=None, **kwargs): sounding = snd.Sounding(None, None) sounding.from_lapse_rate(trial_lapse_rate, 0, 20e3, 10000) parcel = CloudParcel(T0=sounding.surface_temperature + 1, q0=0.01, mix_len=np.inf, w0=0.0, method='RK4') water_core = WaterManager(WaterManager.tanh_vapour_flow, None) parcel.run(0.5, 6800, sounding, WM=water_core) zA = np.copy(parcel.storage['z']) water_core = WaterManager(WaterManager.step_vapour_flow, None) parcel.run(0.5, 6800, sounding, WM=water_core) zB = np.copy(parcel.storage['z']) water_core = WaterManager(WaterManager.step_vapour_flow, None, mult=0.5) parcel.run(0.5, 6800, sounding, WM=water_core) zC = np.copy(parcel.storage['z']) f, ax = plt.subplots() ax.plot(np.arange(parcel.NT) * parcel.dt, zA * 1e-3, label='Hyperbolic Tangent Flow') ax.plot(np.arange(parcel.NT) * parcel.dt, zB * 1e-3, '--', label='Step Flow') ax.plot(np.arange(parcel.NT) * parcel.dt, zC * 1e-3, ':', label='Dampened Step Flow') ax.plot([0.0, parcel.NT * parcel.dt], [0, 0], 'k--', alpha=0.4) ax.plot( [0.0, parcel.NT * parcel.dt], [parcel.storage['z'].max() * 1e-3, parcel.storage['z'].max() * 1e-3], 'k--', alpha=0.4) ax.grid() ax.set_xlabel("Time (s)") ax.set_ylabel("Height (km)") ax.set_xlim(0, parcel.NT * parcel.dt) plt.show() if save_file: f.savefig(save_file, dpi=300, **kwargs)
def test_model_stability(dt=0.5, save_file=None, **kwargs): from scipy.signal import find_peaks sounding = snd.Sounding(None, None) sounding.from_lapse_rate(trial_lapse_rate, 0, 20e3, 10000) methods = ["Euler", "Matsuno", "RK4"] parcels = [ CloudParcel(T0=sounding.surface_temperature + 1., q0=0.02, mix_len=np.inf, w0=0.0, method=method) for method in methods ] DWM = WaterManager(WaterManager.tanh_vapour_flow, None) f, ax = plt.subplots(1, 2, sharey=True, figsize=(9, 4)) for i, mstr, parcel in zip(range(3), methods, parcels): parcel.run(dt, 10000, sounding, WM=DWM) z = parcel.storage['z'] zpeaki = find_peaks(z)[0] zpeaks = z[zpeaki] / z[zpeaki[0]] zmin = -z + z[zpeaki[0]] zthroughi = find_peaks(zmin)[0] zthroughs = zmin[zthroughi] / zmin[zthroughi[0]] ax[0].plot(zpeaki * dt, zpeaks, color='C%i' % i) ax[1].plot(zthroughi * dt, zthroughs, color='C%i' % i, label=mstr) ax[0].grid() ax[1].grid() ax[0].set_xlabel("Time (s)") ax[1].set_xlabel("Time (s)") ax[0].set_ylabel("Relative Peak/Through Height") ax[0].set_xlim(500, dt * z.size) ax[1].set_xlim(500, dt * z.size) ax[0].legend(methods) plt.tight_layout() plt.show() if save_file is not None and type(save_file) is str: f.savefig(save_file, **kwargs)
def test_precip_modules(save_file=None, **kwargs): sounding = snd.Sounding(None, None) sounding.from_lapse_rate(trial_lapse_rate, 0, 20e3, 10000) parcel = CloudParcel(T0=sounding.surface_temperature + 1, q0=sounding.surface_humidity, mix_len=np.inf, w0=0.0, method='RK4') w1 = WaterManager(WaterManager.tanh_vapour_flow, WaterManager.precip_fixed_rate) w2 = WaterManager(WaterManager.tanh_vapour_flow, WaterManager.precip_fixed_amount) w3 = WaterManager(WaterManager.tanh_vapour_flow, WaterManager.precip_tanh_rate) parcel.run(0.5, 7000, sounding, WM=w1) p1 = parcel.storage['p_gkg'] * 1e3 parcel.run(0.5, 7000, sounding, WM=w2) p2 = parcel.storage['p_gkg'] * 1e3 parcel.run(0.5, 7000, sounding, WM=w3) p3 = parcel.storage['p_gkg'] * 1e3 f, ax = plt.subplots() ax.plot(np.arange(parcel.NT) * parcel.dt, p1, ':') ax.plot(np.arange(parcel.NT) * parcel.dt, p2, '-') ax.plot(np.arange(parcel.NT) * parcel.dt, p3, '--') ax.grid() ax.set_xlabel("Time (s)") ax.set_ylabel("Precipitated Water (g/kg)") ax.set_xlim(0, parcel.NT * parcel.dt) if save_file is not None: f.savefig(save_file, dpi=300, **kwargs) plt.show()
if test_model and __name__ == '__main__': def trial_lapse_rate(z): Tv = 0.0 Td = 0.0 if 0.0 <= z < 1500.0: Tv = -10.0e-3 Td = 1e-4 elif 1500.0 <= z < 10000.0: Tv = -6.5e-3 Td = -8e-3 else: Tv = 1e-3 Td = -9.8e-4 return {'T' : Tv, 'Td' : Td} sounding = snd.Sounding(None, None) sounding.from_lapse_rate(trial_lapse_rate, 0, 2e4, 10000) # Setup sim parcel = CCNParcel(T0=sounding.surface_temperature + 1.0, q0=0.01, mix_len=np.inf, ql_kernel=Long_colkernel) parcel.run(0.2, 4500, sounding) #parcel.write_to_netCDF("./ascent_long_kernel.nc") f, ax = sounding.SkewT_logP(show=False) ax.plot(parcel.T, parcel.p * 1e-2) plt.show() # Test Collision Growth Module if test_collision and __name__ == '__main__': R = prdist(69, 0.25, 0.055, mode='linexp')
def read(self, mwx_file): def _get_flighttime(radio_time, start_time, launch_time): """ f_flighttime = lambda radio_time: start_time + dt.timedelta( seconds=radio_time - np.float(launch_time) ) """ return start_time + dt.timedelta(seconds=radio_time - np.float(launch_time)) with rh.MWX(mwx_file) as mwx: decompressed_files = mwx.decompressed_files # Get the files SynchronizedSoundingData.xml, Soundings.xml, ... a1, sync_filename = rh.check_availability( decompressed_files, "SynchronizedSoundingData.xml", True) a2, snd_filename = rh.check_availability(decompressed_files, "Soundings.xml", True) a3, radio_filename = rh.check_availability(decompressed_files, "Radiosondes.xml", True) if np.any([not a1, not a2, not a3]): logging.warning( "No sounding data found in {}. Skipped".format(mwx_file)) return # Read Soundings.xml to get base time itemlist = rh.read_xml(snd_filename) for i, item in enumerate(itemlist): begin_time = item.attributes["BeginTime"].value launch_time = item.attributes["LaunchTime"].value station_altitude = item.attributes["Altitude"].value begin_time_dt = dt.datetime.strptime(begin_time, "%Y-%m-%dT%H:%M:%S.%f") # Read sounding data pd_snd = rh.get_sounding_profile(sync_filename, self.sync_sounding_values) # Read Radiosounding.xml to get sounding metadata sounding_meta_dict = rh.get_sounding_metadata( radio_filename, self.radiosondes_values) sounding_meta_dict["source"] = str(mwx_file) pd_snd = rh.rename_variables(pd_snd, self.variable_name_mapping) sounding_meta_dict = rh.rename_metadata(sounding_meta_dict, self.variable_name_mapping) # Attach units where provided import pandas as pd import pint import pint_pandas as pp ureg = pint.UnitRegistry() ureg.define("fraction = [] = frac") ureg.define("percent = 1e-2 frac = pct") pp.PintType.ureg = ureg PA_ = pp.PintArray pd_snd_w_units = pd.DataFrame() for var in pd_snd.columns: if var in self.units.keys(): pd_snd_w_units[var] = PA_(pd_snd[var].values, dtype=self.units[var]) else: # no units found pd_snd_w_units[var] = pd_snd[var].values pd_snd = pd_snd_w_units # Create flight time f_flighttime = partial(_get_flighttime, start_time=begin_time_dt, launch_time=launch_time) pd_snd["flight_time"] = pd_snd.RadioRxTimePk.apply(f_flighttime) # Write to class sounding = snd.Sounding() sounding.profile = pd_snd sounding.meta_data = sounding_meta_dict sounding.meta_data["launch_time"] = launch_time sounding.meta_data["begin_time"] = begin_time_dt sounding.meta_data["station_altitude"] = station_altitude sounding.unitregistry = ureg return sounding