use earth::atmosphere::climate::{
CLIMATE_SENSITIVITY_K, ClimateState, EARTH_ALBEDO, PRE_INDUSTRIAL_CO2_PPM,
co2_doubling_forcing, planck_spectral_radiance, solar_zenith,
};
use earth::atmosphere::heatwaves::{HeatWave, dew_point_c, saturation_vapor_pressure_pa};
use earth::atmosphere::layers::{
LAPSE_RATE_TROPOSPHERE, SEA_LEVEL_PRESSURE, SEA_LEVEL_TEMPERATURE, barometric_pressure,
dry_air_molar_mass, mesosphere, scale_height, stratosphere, thermosphere, troposphere,
};
use earth::atmosphere::storms::{TropicalCyclone, cape_integrated, cape_layer, fujita_scale};
use earth::atmosphere::winds::{
OMEGA_EARTH, beaufort_to_m_s, coriolis_parameter, ekman_spiral_depth, geostrophic_wind_speed,
gradient_wind_speed, thermal_wind_shear, wind_chill_temperature,
};
use earth::hydrology::glaciers::{
GLEN_FLOW_LAW_A, ICE_CREEP_EXPONENT, antarctic_ice_sheet, greenland_ice_sheet, ice_density,
ice_rheology_viscosity,
};
use earth::hydrology::lakes::{baikal, superior};
use earth::hydrology::oceans::{
MEAN_OCEAN_DEPTH_M, MEAN_SALINITY_PSU, OCEAN_SURFACE_AREA_M2, OCEAN_VOLUME_M3,
SEAWATER_DENSITY, deep_ocean, dissolved_gas_henry, ocean_area_from_fraction,
ocean_heat_content_j, sea_level_rise_thermal_m, surface_longwave_radiation_w_m2,
surface_mixed_layer, thermocline, thermohaline_overturning_rate_sv, vapor_pressure_over_ocean,
};
use earth::hydrology::rivers::{amazon, chezy_velocity, hjulstrom_erosion_threshold, nile};
fn main() {
let tropo = troposphere();
let strato = stratosphere();
let meso = mesosphere();
let thermo = thermosphere();
let altitudes = [0.0, 5000.0, 11000.0, 20000.0, 50000.0, 80000.0];
let mut total_density = 0.0;
for &alt in &altitudes {
let layer = if alt < 12_000.0 {
&tropo
} else if alt < 50_000.0 {
&strato
} else if alt < 85_000.0 {
&meso
} else {
&thermo
};
let temp = layer.temperature_at(alt);
let press = layer.pressure_at(alt);
let dens = layer.density_at(alt);
total_density += dens;
println!(
"[{:>12}] alt={:>6.0}m T={:.1}K P={:.0}Pa ρ={:.4}kg/m³",
layer.name, alt, temp, press, dens
);
}
let p_sea = barometric_pressure(0.0);
let p_cruise = barometric_pressure(10_000.0);
let h_scale = scale_height();
println!(
"P(sea)={:.0}Pa P(10km)={:.0}Pa H_scale={:.0}m Σρ={:.4}",
p_sea, p_cruise, h_scale, total_density
);
println!(
"constants: P0={} T0={} M_air={} Γ={}",
SEA_LEVEL_PRESSURE,
SEA_LEVEL_TEMPERATURE,
dry_air_molar_mass(),
LAPSE_RATE_TROPOSPHERE
);
let pre_ind = ClimateState::pre_industrial();
let current = ClimateState::current();
let forcing_pi = pre_ind.co2_radiative_forcing();
let forcing_now = current.co2_radiative_forcing();
let warming = current.equilibrium_warming();
let olr = current.outgoing_longwave_radiation();
let asr = current.absorbed_solar_radiation();
let imbalance = current.energy_imbalance();
let t_eff = current.effective_emission_temperature();
let greenhouse = current.greenhouse_effect_k();
println!(
"CO2: pre-ind={:.0}ppm now={:.0}ppm",
pre_ind.co2_ppm, current.co2_ppm
);
println!(
"Forcing: pi={:.2} now={:.2} W/m² warming={:.2}K",
forcing_pi, forcing_now, warming
);
println!(
"OLR={:.1} ASR={:.1} imbalance={:.2} T_eff={:.1}K greenhouse={:.1}K",
olr, asr, imbalance, t_eff, greenhouse
);
let zenith = solar_zenith(45.0, 23.44, 0.0);
let radiance = planck_spectral_radiance(10e-6, 288.0);
let doubling = co2_doubling_forcing();
println!(
"zenith={:.2}° planck(10µm,288K)={:.4} 2xCO2={:.2}W/m²",
zenith, radiance, doubling
);
println!(
"constants: CO2_PI={} sensitivity={} albedo={}",
PRE_INDUSTRIAL_CO2_PPM, CLIMATE_SENSITIVITY_K, EARTH_ALBEDO
);
let cyclone = TropicalCyclone {
max_sustained_wind_m_s: 75.0,
central_pressure_hpa: 940.0,
radius_max_wind_km: 30.0,
latitude_deg: 20.0,
};
let cat = cyclone.saffir_simpson_category();
let ace = cyclone.accumulated_cyclone_energy(48.0);
let pi = TropicalCyclone::potential_intensity_m_s(302.0, 200.0, 1500.0);
let rossby = cyclone.rossby_deformation_radius();
let wind_r = cyclone.wind_at_radius(60.0);
let fujita = fujita_scale(90.0);
let cape_single = cape_layer(305.0, 300.0, 1000.0);
let cape = cape_integrated(305.0, 300.0, 0.0075, 500.0, 40);
println!(
"Cyclone: cat={} ACE={:.1} PI={:.1}m/s Rossby={:.0}m wind@60km={:.1}m/s",
cat, ace, pi, rossby, wind_r
);
println!(
"Fujita(90m/s)={} CAPE_layer={:.1} CAPE_integrated={:.1}J/kg",
fujita, cape_single, cape
);
let f_45 = coriolis_parameter(45.0);
let vg = geostrophic_wind_speed(0.01, 45.0, 1.225);
let vgr = gradient_wind_speed(0.01, 500_000.0, 45.0, 1.225);
let tw = thermal_wind_shear(5e-6, 260.0, 45.0, 500e2, 750e2);
let ekman = ekman_spiral_depth(0.05, 45.0);
let b7 = beaufort_to_m_s(7);
let wc = wind_chill_temperature(-10.0, 30.0);
println!(
"ω={:.5e} f(45°)={:.5e} Vg={:.1} Vgr={:.1} thermal_wind={:.4}",
OMEGA_EARTH, f_45, vg, vgr, tw
);
println!(
"Ekman={:.0}m B7={:.1}m/s windchill(-10°,30km/h)={:.1}°C",
ekman, b7, wc
);
let hw = HeatWave {
max_temperature_c: 45.0,
duration_days: 5,
relative_humidity_percent: 40.0,
};
let hi = hw.heat_index_c();
let wb = hw.wet_bulb_temperature_c();
let danger = hw.danger_level();
let mort = hw.excess_mortality_factor();
let svp = saturation_vapor_pressure_pa(35.0);
let dp = dew_point_c(35.0, 60.0);
println!(
"Heatwave: HI={:.1}°C Tw={:.1}°C danger={} mortality_factor={:.2}",
hi, wb, danger, mort
);
println!("SVP(35°C)={:.0}Pa dewpoint(35°C,60%)={:.1}°C", svp, dp);
let sml = surface_mixed_layer();
let tc = thermocline();
let deep = deep_ocean();
let rho_sml = sml.density_kg_m3();
let rho_tc = tc.density_kg_m3();
let rho_deep = deep.density_kg_m3();
let speed_sml = sml.sound_speed_m_s();
let p_deep = deep.pressure_at_depth(3000.0);
let thc = thermohaline_overturning_rate_sv();
let ohc = ocean_heat_content_j(0.5, 700.0);
let slr = sea_level_rise_thermal_m(0.5, 700.0);
let lw = surface_longwave_radiation_w_m2(17.0, 0.97);
let oa = ocean_area_from_fraction(0.71);
let vp = vapor_pressure_over_ocean(20.0);
let co2_dissolved = dissolved_gas_henry(40.0, 15.0, 3.4e-4);
println!(
"Ocean: ρ_sml={:.1} ρ_tc={:.1} ρ_deep={:.1} sound={:.0}m/s P@3km={:.0}Pa",
rho_sml, rho_tc, rho_deep, speed_sml, p_deep
);
println!(
"THC={:.0}Sv OHC={:.2e}J SLR={:.4}m LW={:.1}W/m²",
thc, ohc, slr, lw
);
println!(
"area(0.71)={:.2e}m² VP(20°C)={:.0}Pa CO2_diss={:.6}mol/m³",
oa, vp, co2_dissolved
);
println!(
"constants: A={:.2e}m² D={:.0}m V={:.3e}m³ S={:.0}psu ρ={:.0}",
OCEAN_SURFACE_AREA_M2,
MEAN_OCEAN_DEPTH_M,
OCEAN_VOLUME_M3,
MEAN_SALINITY_PSU,
SEAWATER_DENSITY
);
let am = amazon();
let ni = nile();
let v_manning = am.manning_velocity(3.0, 0.035);
let fr = am.froude_number(1.5, 10.0);
let re = ni.reynolds_number(1.0, 5.0);
let sed = am.sediment_transport_capacity(1.5, 10.0, 0.001);
let sp = am.stream_power_w_per_m();
let sd = ni.specific_discharge_m_s();
let chezy = chezy_velocity(50.0, 2.0, 0.001);
let hjul = hjulstrom_erosion_threshold(0.5);
println!(
"Amazon: V_manning={:.2}m/s Fr={:.3} sed={:.4} SP={:.0}W/m",
v_manning, fr, sed, sp
);
println!(
"Nile: Re={:.0} q={:.2e}m/s Chézy={:.2}m/s Hjul(0.5mm)={:.3}m/s",
re, sd, chezy, hjul
);
let bk = baikal();
let su = superior();
let d_bk = bk.mean_depth_m();
let sdl = su.shoreline_development_ratio(4385.0);
let rt = bk.residence_time_years(330.0);
let strat = su.thermal_stratification_energy_j(18.0, 4.0);
let evap = su.evaporation_rate_mm_day(25.0, 18.0, 3.0, 60.0);
let lw_lake = bk.longwave_radiation_w_m2(4.0, 0.97);
println!(
"Baikal: mean_d={:.1}m res_time={:.0}yr LW={:.1}W/m²",
d_bk, rt, lw_lake
);
println!(
"Superior: SDL={:.2} strat_E={:.2e}J evap={:.2}mm/d",
sdl, strat, evap
);
let ant = antarctic_ice_sheet();
let grl = greenland_ice_sheet();
let mb_ant = ant.mass_balance_m_yr();
let tau_ant = ant.basal_shear_stress_pa();
let vel_ant = ant.deformation_velocity_m_yr();
let ela = grl.equilibrium_line_altitude(0.0);
let vol = grl.volume_m3(800_000.0);
let sle = grl.sea_level_equivalent_mm(800_000.0);
let visc = ice_rheology_viscosity(-10.0, 100_000.0);
println!(
"Antarctic: MB={:.3}m/yr τ={:.0}Pa v={:.4}m/yr",
mb_ant, tau_ant, vel_ant
);
println!(
"Greenland: ELA={:.0}m V={:.2e}m³ SLE={:.1}mm visc={:.2e}Pa·s",
ela, vol, sle, visc
);
println!(
"constants: ρ_ice={} n={} A_glen={:.2e}",
ice_density(),
ICE_CREEP_EXPONENT,
GLEN_FLOW_LAW_A
);
}