physicskit 0.1.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- physicskit/__init__.py +51 -0
- physicskit/astro/__init__.py +66 -0
- physicskit/astro/cosmic_web.py +395 -0
- physicskit/astro/galactic_dynamics.py +137 -0
- physicskit/astro/nbody.py +208 -0
- physicskit/astro/orbital_mechanics.py +220 -0
- physicskit/astro/stellar_dynamo.py +628 -0
- physicskit/astro/stellar_structure.py +198 -0
- physicskit/astro/tests/__init__.py +0 -0
- physicskit/astro/tests/conftest.py +7 -0
- physicskit/astro/tests/test_cosmic_web.py +159 -0
- physicskit/astro/tests/test_galactic_dynamics.py +46 -0
- physicskit/astro/tests/test_nbody.py +81 -0
- physicskit/astro/tests/test_orbital_mechanics.py +73 -0
- physicskit/astro/tests/test_stellar_dynamo.py +198 -0
- physicskit/astro/tests/test_stellar_structure.py +52 -0
- physicskit/astro/tests/test_visualizers.py +159 -0
- physicskit/astro/visualizers.py +628 -0
- physicskit/chaos/__init__.py +55 -0
- physicskit/chaos/core/__init__.py +3 -0
- physicskit/chaos/core/base_system.py +342 -0
- physicskit/chaos/core/integrators.py +40 -0
- physicskit/chaos/exceptions.py +24 -0
- physicskit/chaos/quantum/__init__.py +38 -0
- physicskit/chaos/quantum/billiards.py +274 -0
- physicskit/chaos/quantum/husimi.py +85 -0
- physicskit/chaos/quantum/maps.py +366 -0
- physicskit/chaos/systems/__init__.py +38 -0
- physicskit/chaos/systems/billiards.py +1131 -0
- physicskit/chaos/systems/continuous.py +1276 -0
- physicskit/chaos/systems/maps.py +557 -0
- physicskit/chaos/tests/__init__.py +0 -0
- physicskit/chaos/tests/test_basins.py +76 -0
- physicskit/chaos/tests/test_bifurcation.py +132 -0
- physicskit/chaos/tests/test_billiards.py +115 -0
- physicskit/chaos/tests/test_continuous.py +224 -0
- physicskit/chaos/tests/test_dimension.py +69 -0
- physicskit/chaos/tests/test_divergence.py +90 -0
- physicskit/chaos/tests/test_dynamic_plots.py +269 -0
- physicskit/chaos/tests/test_integrators.py +96 -0
- physicskit/chaos/tests/test_io.py +41 -0
- physicskit/chaos/tests/test_maps.py +110 -0
- physicskit/chaos/tests/test_metrics.py +115 -0
- physicskit/chaos/tests/test_phase_space.py +73 -0
- physicskit/chaos/tests/test_properties.py +116 -0
- physicskit/chaos/tests/test_quantum_billiards.py +94 -0
- physicskit/chaos/tests/test_quantum_maps.py +144 -0
- physicskit/chaos/tests/test_recurrence.py +51 -0
- physicskit/chaos/tests/test_repr_and_api_consistency.py +134 -0
- physicskit/chaos/tests/test_section.py +49 -0
- physicskit/chaos/tests/test_spectral.py +48 -0
- physicskit/chaos/tests/test_streamlit_app.py +45 -0
- physicskit/chaos/tests/test_timeseries.py +131 -0
- physicskit/chaos/tests/test_viewer3d.py +41 -0
- physicskit/chaos/utils/__init__.py +46 -0
- physicskit/chaos/utils/dimension.py +139 -0
- physicskit/chaos/utils/io.py +95 -0
- physicskit/chaos/utils/metrics.py +304 -0
- physicskit/chaos/utils/recurrence.py +122 -0
- physicskit/chaos/utils/spectral.py +69 -0
- physicskit/chaos/utils/timeseries.py +303 -0
- physicskit/chaos/visualizers/__init__.py +85 -0
- physicskit/chaos/visualizers/basins.py +185 -0
- physicskit/chaos/visualizers/bifurcation.py +273 -0
- physicskit/chaos/visualizers/divergence.py +374 -0
- physicskit/chaos/visualizers/dynamic_plots.py +1372 -0
- physicskit/chaos/visualizers/phase_space.py +133 -0
- physicskit/chaos/visualizers/quantum.py +299 -0
- physicskit/chaos/visualizers/recurrence.py +91 -0
- physicskit/chaos/visualizers/section.py +161 -0
- physicskit/chaos/visualizers/theme.py +31 -0
- physicskit/chaos/visualizers/viewer3d.py +82 -0
- physicskit/classical/__init__.py +55 -0
- physicskit/classical/core/__init__.py +17 -0
- physicskit/classical/core/base_system.py +510 -0
- physicskit/classical/core/integrators.py +397 -0
- physicskit/classical/systems/__init__.py +32 -0
- physicskit/classical/systems/chains.py +334 -0
- physicskit/classical/systems/hamiltonian.py +215 -0
- physicskit/classical/systems/lagrangian.py +308 -0
- physicskit/classical/systems/newtonian.py +536 -0
- physicskit/classical/systems/rotations.py +614 -0
- physicskit/classical/tests/__init__.py +0 -0
- physicskit/classical/tests/conftest.py +7 -0
- physicskit/classical/tests/test_base_system.py +113 -0
- physicskit/classical/tests/test_chains.py +84 -0
- physicskit/classical/tests/test_conservation.py +244 -0
- physicskit/classical/tests/test_conservation_utils.py +47 -0
- physicskit/classical/tests/test_hamiltonian.py +44 -0
- physicskit/classical/tests/test_integrators.py +123 -0
- physicskit/classical/tests/test_lagrangian.py +69 -0
- physicskit/classical/tests/test_newtonian.py +45 -0
- physicskit/classical/tests/test_rotations.py +160 -0
- physicskit/classical/tests/test_stepsize.py +149 -0
- physicskit/classical/tests/test_symbolic.py +125 -0
- physicskit/classical/tests/test_visualizers.py +172 -0
- physicskit/classical/utils/__init__.py +20 -0
- physicskit/classical/utils/conservation.py +126 -0
- physicskit/classical/utils/stepsize.py +187 -0
- physicskit/classical/utils/symbolic.py +235 -0
- physicskit/classical/visualizers/__init__.py +25 -0
- physicskit/classical/visualizers/animations.py +508 -0
- physicskit/classical/visualizers/interactive.py +113 -0
- physicskit/classical/visualizers/modal_analysis.py +97 -0
- physicskit/classical/visualizers/phase_space.py +214 -0
- physicskit/condensed/__init__.py +122 -0
- physicskit/condensed/anderson_localization.py +155 -0
- physicskit/condensed/correlated.py +284 -0
- physicskit/condensed/ginzburg_landau.py +220 -0
- physicskit/condensed/landau_levels.py +246 -0
- physicskit/condensed/laughlin.py +229 -0
- physicskit/condensed/models.py +627 -0
- physicskit/condensed/tests/__init__.py +0 -0
- physicskit/condensed/tests/test_condensed.py +518 -0
- physicskit/condensed/tests/test_visualizers.py +87 -0
- physicskit/condensed/tight_binding.py +445 -0
- physicskit/condensed/topological_insulator_3d.py +178 -0
- physicskit/condensed/topology.py +217 -0
- physicskit/condensed/visualizers.py +296 -0
- physicskit/condensed/weyl.py +180 -0
- physicskit/constants.py +184 -0
- physicskit/fields/__init__.py +111 -0
- physicskit/fields/electrodynamics.py +671 -0
- physicskit/fields/quantum_fields.py +510 -0
- physicskit/fields/solitons.py +527 -0
- physicskit/fields/tests/__init__.py +0 -0
- physicskit/fields/tests/conftest.py +7 -0
- physicskit/fields/tests/test_field_animations.py +154 -0
- physicskit/fields/tests/test_fields.py +439 -0
- physicskit/fields/tests/test_visualizers.py +101 -0
- physicskit/fields/visualizers.py +503 -0
- physicskit/fluids/__init__.py +134 -0
- physicskit/fluids/core/__init__.py +23 -0
- physicskit/fluids/core/grid.py +165 -0
- physicskit/fluids/core/timestepping.py +231 -0
- physicskit/fluids/exceptions.py +26 -0
- physicskit/fluids/systems/__init__.py +70 -0
- physicskit/fluids/systems/compressible_flow.py +281 -0
- physicskit/fluids/systems/instabilities.py +343 -0
- physicskit/fluids/systems/navier_stokes.py +221 -0
- physicskit/fluids/systems/potential_flow.py +440 -0
- physicskit/fluids/systems/viscous_flow.py +425 -0
- physicskit/fluids/systems/vortex_dynamics.py +304 -0
- physicskit/fluids/tests/__init__.py +0 -0
- physicskit/fluids/tests/conftest.py +7 -0
- physicskit/fluids/tests/test_compressible_flow.py +66 -0
- physicskit/fluids/tests/test_instabilities.py +115 -0
- physicskit/fluids/tests/test_navier_stokes.py +67 -0
- physicskit/fluids/tests/test_potential_flow.py +92 -0
- physicskit/fluids/tests/test_static_visualizers.py +91 -0
- physicskit/fluids/tests/test_utils.py +100 -0
- physicskit/fluids/tests/test_viscous_flow.py +110 -0
- physicskit/fluids/tests/test_visualizers.py +34 -0
- physicskit/fluids/tests/test_vortex_dynamics.py +88 -0
- physicskit/fluids/utils/__init__.py +18 -0
- physicskit/fluids/utils/dimensionless.py +239 -0
- physicskit/fluids/utils/spectral_analysis.py +142 -0
- physicskit/fluids/visualizers/__init__.py +14 -0
- physicskit/fluids/visualizers/compressible.py +39 -0
- physicskit/fluids/visualizers/flow_fields.py +252 -0
- physicskit/fluids/visualizers/potential_flow.py +51 -0
- physicskit/fluids/visualizers/spectra.py +62 -0
- physicskit/fluids/visualizers/theme.py +38 -0
- physicskit/integrators/__init__.py +52 -0
- physicskit/integrators/adaptive.py +199 -0
- physicskit/integrators/fixed_step.py +360 -0
- physicskit/integrators/tests/__init__.py +0 -0
- physicskit/integrators/tests/test_integrators.py +101 -0
- physicskit/optics/__init__.py +124 -0
- physicskit/optics/_compat.py +5 -0
- physicskit/optics/gaussian.py +382 -0
- physicskit/optics/quantum_optics.py +428 -0
- physicskit/optics/ray.py +469 -0
- physicskit/optics/tests/__init__.py +0 -0
- physicskit/optics/tests/test_diffraction_animation.py +38 -0
- physicskit/optics/tests/test_gaussian.py +170 -0
- physicskit/optics/tests/test_quantum_optics.py +147 -0
- physicskit/optics/tests/test_ray.py +177 -0
- physicskit/optics/tests/test_visualizers.py +58 -0
- physicskit/optics/tests/test_wave.py +146 -0
- physicskit/optics/visualizers.py +264 -0
- physicskit/optics/wave.py +365 -0
- physicskit/particle/__init__.py +152 -0
- physicskit/particle/collider.py +382 -0
- physicskit/particle/confinement.py +125 -0
- physicskit/particle/decays.py +357 -0
- physicskit/particle/electroweak.py +300 -0
- physicskit/particle/kinematics.py +271 -0
- physicskit/particle/neutrinos.py +84 -0
- physicskit/particle/nuclear.py +100 -0
- physicskit/particle/scattering.py +159 -0
- physicskit/particle/tests/__init__.py +0 -0
- physicskit/particle/tests/conftest.py +7 -0
- physicskit/particle/tests/test_collider.py +119 -0
- physicskit/particle/tests/test_confinement.py +42 -0
- physicskit/particle/tests/test_decays.py +112 -0
- physicskit/particle/tests/test_electroweak.py +97 -0
- physicskit/particle/tests/test_kinematics.py +138 -0
- physicskit/particle/tests/test_neutrinos.py +36 -0
- physicskit/particle/tests/test_nuclear.py +45 -0
- physicskit/particle/tests/test_scattering.py +64 -0
- physicskit/particle/tests/test_visualizers.py +214 -0
- physicskit/particle/visualizers/__init__.py +38 -0
- physicskit/particle/visualizers/animations.py +705 -0
- physicskit/particle/visualizers/static.py +101 -0
- physicskit/plasma/__init__.py +176 -0
- physicskit/plasma/acceleration.py +152 -0
- physicskit/plasma/instabilities.py +417 -0
- physicskit/plasma/kinetic.py +588 -0
- physicskit/plasma/mhd.py +463 -0
- physicskit/plasma/single_particle.py +562 -0
- physicskit/plasma/tests/__init__.py +0 -0
- physicskit/plasma/tests/conftest.py +7 -0
- physicskit/plasma/tests/test_new_time_domain_features.py +222 -0
- physicskit/plasma/tests/test_plasma.py +232 -0
- physicskit/plasma/tests/test_visualizers.py +79 -0
- physicskit/plasma/turbulence.py +219 -0
- physicskit/plasma/visualizers.py +868 -0
- physicskit/plasma/waves.py +549 -0
- physicskit/quantum/__init__.py +180 -0
- physicskit/quantum/_compat.py +20 -0
- physicskit/quantum/chapters/__init__.py +0 -0
- physicskit/quantum/chapters/entanglement.py +489 -0
- physicskit/quantum/chapters/harmonic_spin.py +517 -0
- physicskit/quantum/chapters/hydrogen_am.py +292 -0
- physicskit/quantum/chapters/perturbation.py +350 -0
- physicskit/quantum/chapters/potentials.py +997 -0
- physicskit/quantum/chapters/spin.py +306 -0
- physicskit/quantum/chapters/wave_packets.py +541 -0
- physicskit/quantum/core/__init__.py +0 -0
- physicskit/quantum/core/eigensolvers.py +311 -0
- physicskit/quantum/core/operators.py +296 -0
- physicskit/quantum/core/solvers.py +271 -0
- physicskit/quantum/tests/__init__.py +0 -0
- physicskit/quantum/tests/conftest.py +7 -0
- physicskit/quantum/tests/test_animations.py +225 -0
- physicskit/quantum/tests/test_compat.py +43 -0
- physicskit/quantum/tests/test_eigensolvers.py +24 -0
- physicskit/quantum/tests/test_entanglement.py +127 -0
- physicskit/quantum/tests/test_harmonic_spin.py +140 -0
- physicskit/quantum/tests/test_hydrogen_am.py +48 -0
- physicskit/quantum/tests/test_measure.py +110 -0
- physicskit/quantum/tests/test_operators.py +105 -0
- physicskit/quantum/tests/test_perturbation.py +112 -0
- physicskit/quantum/tests/test_physics_checks.py +131 -0
- physicskit/quantum/tests/test_potentials.py +191 -0
- physicskit/quantum/tests/test_solvers.py +70 -0
- physicskit/quantum/tests/test_spin.py +22 -0
- physicskit/quantum/tests/test_unitarity.py +84 -0
- physicskit/quantum/tests/test_wave_packets.py +53 -0
- physicskit/quantum/utils/__init__.py +0 -0
- physicskit/quantum/utils/measure.py +253 -0
- physicskit/quantum/visualizers/__init__.py +0 -0
- physicskit/quantum/visualizers/bloch_sphere.py +205 -0
- physicskit/quantum/visualizers/entanglement.py +58 -0
- physicskit/quantum/visualizers/orbitals.py +187 -0
- physicskit/quantum/visualizers/phase_space.py +179 -0
- physicskit/quantum/visualizers/wavefunctions.py +230 -0
- physicskit/relativity/__init__.py +61 -0
- physicskit/relativity/chapters/__init__.py +33 -0
- physicskit/relativity/chapters/cosmology.py +190 -0
- physicskit/relativity/chapters/gw_merger.py +399 -0
- physicskit/relativity/chapters/kerr.py +371 -0
- physicskit/relativity/chapters/lensing.py +196 -0
- physicskit/relativity/chapters/neutron_star.py +149 -0
- physicskit/relativity/chapters/schwarzschild.py +412 -0
- physicskit/relativity/chapters/timekeeping.py +133 -0
- physicskit/relativity/core/__init__.py +12 -0
- physicskit/relativity/core/geodesics.py +216 -0
- physicskit/relativity/core/kerr_raytracer.py +259 -0
- physicskit/relativity/core/raytracer.py +241 -0
- physicskit/relativity/core/tensors.py +468 -0
- physicskit/relativity/tests/__init__.py +0 -0
- physicskit/relativity/tests/test_conservations.py +54 -0
- physicskit/relativity/tests/test_constants.py +34 -0
- physicskit/relativity/tests/test_cosmology.py +61 -0
- physicskit/relativity/tests/test_gw_merger.py +117 -0
- physicskit/relativity/tests/test_kerr.py +116 -0
- physicskit/relativity/tests/test_kerr_raytracer.py +103 -0
- physicskit/relativity/tests/test_lensing.py +75 -0
- physicskit/relativity/tests/test_neutron_star.py +48 -0
- physicskit/relativity/tests/test_raytracer.py +67 -0
- physicskit/relativity/tests/test_schwarzschild.py +126 -0
- physicskit/relativity/tests/test_shadow_render.py +81 -0
- physicskit/relativity/tests/test_tensors.py +86 -0
- physicskit/relativity/tests/test_timekeeping.py +51 -0
- physicskit/relativity/tests/test_visualizers_misc.py +115 -0
- physicskit/relativity/utils/__init__.py +1 -0
- physicskit/relativity/utils/constants.py +232 -0
- physicskit/relativity/visualizers/__init__.py +46 -0
- physicskit/relativity/visualizers/interactive.py +127 -0
- physicskit/relativity/visualizers/shadow_render.py +367 -0
- physicskit/relativity/visualizers/spacetime_3d.py +92 -0
- physicskit/relativity/visualizers/spacetime_diagrams.py +198 -0
- physicskit/relativity/visualizers/wave_plots.py +185 -0
- physicskit/rmt/__init__.py +8 -0
- physicskit/rmt/ensembles/__init__.py +108 -0
- physicskit/rmt/ensembles/banded.py +114 -0
- physicskit/rmt/ensembles/base.py +135 -0
- physicskit/rmt/ensembles/bdg.py +218 -0
- physicskit/rmt/ensembles/chiral.py +308 -0
- physicskit/rmt/ensembles/circular.py +104 -0
- physicskit/rmt/ensembles/crossover.py +82 -0
- physicskit/rmt/ensembles/density_matrix.py +148 -0
- physicskit/rmt/ensembles/effective_hamiltonian.py +230 -0
- physicskit/rmt/ensembles/embedded.py +207 -0
- physicskit/rmt/ensembles/gaussian.py +153 -0
- physicskit/rmt/ensembles/ginibre.py +110 -0
- physicskit/rmt/ensembles/girko.py +190 -0
- physicskit/rmt/ensembles/graph_laplacian.py +92 -0
- physicskit/rmt/ensembles/haar.py +57 -0
- physicskit/rmt/ensembles/jacobi.py +182 -0
- physicskit/rmt/ensembles/poisson.py +77 -0
- physicskit/rmt/ensembles/polynomial.py +139 -0
- physicskit/rmt/ensembles/pt_symmetric.py +120 -0
- physicskit/rmt/ensembles/single_ring.py +170 -0
- physicskit/rmt/ensembles/sparse.py +95 -0
- physicskit/rmt/ensembles/syk.py +170 -0
- physicskit/rmt/ensembles/truncated_unitary.py +80 -0
- physicskit/rmt/ensembles/universality.py +92 -0
- physicskit/rmt/ensembles/wishart.py +88 -0
- physicskit/rmt/py.typed +0 -0
- physicskit/rmt/spectrum.py +82 -0
- physicskit/rmt/stats/__init__.py +160 -0
- physicskit/rmt/stats/characteristic_polynomial.py +77 -0
- physicskit/rmt/stats/circular_law.py +54 -0
- physicskit/rmt/stats/correlations.py +162 -0
- physicskit/rmt/stats/density.py +70 -0
- physicskit/rmt/stats/entanglement.py +36 -0
- physicskit/rmt/stats/free_probability.py +202 -0
- physicskit/rmt/stats/localization.py +338 -0
- physicskit/rmt/stats/marchenko_pastur.py +55 -0
- physicskit/rmt/stats/pt_symmetric.py +265 -0
- physicskit/rmt/stats/ratios.py +110 -0
- physicskit/rmt/stats/real_ginibre.py +134 -0
- physicskit/rmt/stats/rigidity.py +272 -0
- physicskit/rmt/stats/single_ring.py +95 -0
- physicskit/rmt/stats/spacing.py +150 -0
- physicskit/rmt/stats/tracy_widom.py +175 -0
- physicskit/rmt/stats/truncated_unitary.py +40 -0
- physicskit/rmt/stats/unfolding.py +37 -0
- physicskit/rmt/stats/wachter.py +67 -0
- physicskit/rmt/tests/__init__.py +0 -0
- physicskit/rmt/tests/cache_utils.py +107 -0
- physicskit/rmt/tests/conftest.py +8 -0
- physicskit/rmt/tests/test_banded.py +86 -0
- physicskit/rmt/tests/test_base.py +29 -0
- physicskit/rmt/tests/test_bdg.py +133 -0
- physicskit/rmt/tests/test_characteristic_polynomial.py +50 -0
- physicskit/rmt/tests/test_chiral.py +273 -0
- physicskit/rmt/tests/test_circular.py +225 -0
- physicskit/rmt/tests/test_crossover.py +72 -0
- physicskit/rmt/tests/test_density.py +23 -0
- physicskit/rmt/tests/test_density_matrix.py +181 -0
- physicskit/rmt/tests/test_effective_hamiltonian.py +140 -0
- physicskit/rmt/tests/test_embedded.py +169 -0
- physicskit/rmt/tests/test_free_probability.py +81 -0
- physicskit/rmt/tests/test_gaussian_ensembles.py +22 -0
- physicskit/rmt/tests/test_gaussian_semicircle.py +127 -0
- physicskit/rmt/tests/test_ginibre_circular_law.py +131 -0
- physicskit/rmt/tests/test_girko.py +178 -0
- physicskit/rmt/tests/test_graph_laplacian.py +102 -0
- physicskit/rmt/tests/test_haar.py +118 -0
- physicskit/rmt/tests/test_jacobi_wachter.py +136 -0
- physicskit/rmt/tests/test_localization.py +240 -0
- physicskit/rmt/tests/test_poisson.py +149 -0
- physicskit/rmt/tests/test_polynomial.py +107 -0
- physicskit/rmt/tests/test_pt_symmetric.py +178 -0
- physicskit/rmt/tests/test_random_state.py +19 -0
- physicskit/rmt/tests/test_real_ginibre.py +112 -0
- physicskit/rmt/tests/test_rigidity_universality.py +167 -0
- physicskit/rmt/tests/test_single_ring.py +132 -0
- physicskit/rmt/tests/test_spacing_and_ratios.py +122 -0
- physicskit/rmt/tests/test_sparse.py +71 -0
- physicskit/rmt/tests/test_spectrum.py +27 -0
- physicskit/rmt/tests/test_syk.py +136 -0
- physicskit/rmt/tests/test_tracy_widom.py +113 -0
- physicskit/rmt/tests/test_tridiagonal.py +41 -0
- physicskit/rmt/tests/test_truncated_unitary.py +80 -0
- physicskit/rmt/tests/test_validation_base.py +25 -0
- physicskit/rmt/tests/test_validation_misc.py +67 -0
- physicskit/rmt/tests/test_wishart_marchenko_pastur.py +120 -0
- physicskit/rmt/utils/__init__.py +0 -0
- physicskit/rmt/utils/haar.py +128 -0
- physicskit/rmt/utils/random_state.py +24 -0
- physicskit/rmt/utils/tridiagonal.py +167 -0
- physicskit/rmt/validation/__init__.py +36 -0
- physicskit/rmt/validation/base.py +126 -0
- physicskit/rmt/validation/circular_law.py +80 -0
- physicskit/rmt/validation/marchenko_pastur.py +53 -0
- physicskit/rmt/validation/ratio_distribution.py +53 -0
- physicskit/rmt/validation/real_ginibre.py +60 -0
- physicskit/rmt/validation/sine_kernel.py +57 -0
- physicskit/rmt/validation/single_ring.py +68 -0
- physicskit/rmt/validation/tracy_widom.py +89 -0
- physicskit/rmt/validation/universality.py +100 -0
- physicskit/rmt/validation/wachter.py +52 -0
- physicskit/rmt/validation/wigner_semicircle.py +40 -0
- physicskit/rmt/validation/wigner_surmise.py +58 -0
- physicskit/semiclassical/__init__.py +94 -0
- physicskit/semiclassical/_compat.py +5 -0
- physicskit/semiclassical/core/__init__.py +41 -0
- physicskit/semiclassical/core/gutzwiller.py +215 -0
- physicskit/semiclassical/core/path_integral.py +594 -0
- physicskit/semiclassical/core/propagators.py +579 -0
- physicskit/semiclassical/core/wkb.py +308 -0
- physicskit/semiclassical/systems/__init__.py +13 -0
- physicskit/semiclassical/systems/scarring.py +278 -0
- physicskit/semiclassical/tests/__init__.py +0 -0
- physicskit/semiclassical/tests/test_gutzwiller.py +35 -0
- physicskit/semiclassical/tests/test_path_integral.py +194 -0
- physicskit/semiclassical/tests/test_propagators.py +82 -0
- physicskit/semiclassical/tests/test_scarring.py +43 -0
- physicskit/semiclassical/tests/test_visualizers.py +89 -0
- physicskit/semiclassical/tests/test_wkb.py +30 -0
- physicskit/semiclassical/visualizers/__init__.py +17 -0
- physicskit/semiclassical/visualizers/gutzwiller.py +55 -0
- physicskit/semiclassical/visualizers/path_integral.py +195 -0
- physicskit/semiclassical/visualizers/propagators.py +89 -0
- physicskit/semiclassical/visualizers/scarring.py +146 -0
- physicskit/semiclassical/visualizers/wkb.py +55 -0
- physicskit/statphys/__init__.py +80 -0
- physicskit/statphys/chapters/__init__.py +43 -0
- physicskit/statphys/chapters/ehrenfest_urn.py +112 -0
- physicskit/statphys/chapters/ising_lattice.py +431 -0
- physicskit/statphys/chapters/kpz_growth.py +129 -0
- physicskit/statphys/chapters/molecular_dynamics.py +258 -0
- physicskit/statphys/chapters/nonequilibrium_work.py +146 -0
- physicskit/statphys/chapters/percolation.py +305 -0
- physicskit/statphys/chapters/random_walk.py +142 -0
- physicskit/statphys/chapters/renormalization.py +148 -0
- physicskit/statphys/chapters/sandpile.py +109 -0
- physicskit/statphys/chapters/spin_glass.py +275 -0
- physicskit/statphys/core/__init__.py +10 -0
- physicskit/statphys/core/kpz_engine.py +53 -0
- physicskit/statphys/core/md_engine.py +157 -0
- physicskit/statphys/core/monte_carlo.py +462 -0
- physicskit/statphys/core/random_walk_engine.py +68 -0
- physicskit/statphys/core/sandpile_engine.py +52 -0
- physicskit/statphys/tests/__init__.py +0 -0
- physicskit/statphys/tests/test_dynamics.py +66 -0
- physicskit/statphys/tests/test_ehrenfest_urn.py +44 -0
- physicskit/statphys/tests/test_finite_size_scaling.py +62 -0
- physicskit/statphys/tests/test_interactive.py +33 -0
- physicskit/statphys/tests/test_ising.py +68 -0
- physicskit/statphys/tests/test_kpz.py +55 -0
- physicskit/statphys/tests/test_landau_theory.py +49 -0
- physicskit/statphys/tests/test_md_engine.py +31 -0
- physicskit/statphys/tests/test_molecular_dynamics.py +72 -0
- physicskit/statphys/tests/test_nonequilibrium_work.py +33 -0
- physicskit/statphys/tests/test_partition_function.py +26 -0
- physicskit/statphys/tests/test_percolation.py +116 -0
- physicskit/statphys/tests/test_potts_model.py +46 -0
- physicskit/statphys/tests/test_random_walk.py +50 -0
- physicskit/statphys/tests/test_renormalization.py +44 -0
- physicskit/statphys/tests/test_sandpile.py +44 -0
- physicskit/statphys/tests/test_spin_glass.py +73 -0
- physicskit/statphys/tests/test_thermodynamics.py +121 -0
- physicskit/statphys/tests/test_xy_model.py +45 -0
- physicskit/statphys/utils/__init__.py +1 -0
- physicskit/statphys/utils/dynamics.py +100 -0
- physicskit/statphys/utils/finite_size_scaling.py +171 -0
- physicskit/statphys/utils/landau_theory.py +151 -0
- physicskit/statphys/utils/partition_function.py +109 -0
- physicskit/statphys/utils/thermodynamics.py +356 -0
- physicskit/statphys/visualizers/__init__.py +87 -0
- physicskit/statphys/visualizers/interactive.py +161 -0
- physicskit/statphys/visualizers/jarzynski_render.py +44 -0
- physicskit/statphys/visualizers/kpz_render.py +65 -0
- physicskit/statphys/visualizers/lattice_render.py +212 -0
- physicskit/statphys/visualizers/particle_render.py +121 -0
- physicskit/statphys/visualizers/random_walk_render.py +106 -0
- physicskit/statphys/visualizers/rg_render.py +45 -0
- physicskit/statphys/visualizers/sandpile_render.py +65 -0
- physicskit/statphys/visualizers/spin_glass_render.py +40 -0
- physicskit/statphys/visualizers/urn_render.py +38 -0
- physicskit/statphys/visualizers/vortex_render.py +84 -0
- physicskit/tests/__init__.py +0 -0
- physicskit/tests/test_constants.py +38 -0
- physicskit-0.1.0.dist-info/METADATA +196 -0
- physicskit-0.1.0.dist-info/RECORD +484 -0
- physicskit-0.1.0.dist-info/WHEEL +5 -0
- physicskit-0.1.0.dist-info/licenses/LICENSE +21 -0
- physicskit-0.1.0.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,357 @@
|
|
|
1
|
+
r"""Two-body decay kinematics and radioactive decay chains.
|
|
2
|
+
|
|
3
|
+
Uses the same natural-unit convention (:math:`c=1`) as
|
|
4
|
+
:mod:`physicskit.particle.kinematics`.
|
|
5
|
+
|
|
6
|
+
- :func:`two_body_decay_momentum`, :func:`two_body_decay` -- the
|
|
7
|
+
kinematics of a parent particle decaying to two daughters.
|
|
8
|
+
- :func:`decay_constant`, :func:`half_life`, :func:`radioactive_decay_number`,
|
|
9
|
+
:func:`activity` -- the exponential radioactive decay law.
|
|
10
|
+
- :func:`bateman_decay_chain` -- the Bateman equations for a linear chain
|
|
11
|
+
of successive radioactive decays.
|
|
12
|
+
- :func:`michel_spectrum`, :func:`sample_michel_electron_energies`,
|
|
13
|
+
:func:`muon_decay_event` -- the three-body :math:`\mu^-\to e^-\bar\nu_\mu\nu_e`
|
|
14
|
+
weak decay and its (unpolarized, massless-electron) Michel energy spectrum.
|
|
15
|
+
"""
|
|
16
|
+
|
|
17
|
+
from __future__ import annotations
|
|
18
|
+
|
|
19
|
+
import numpy as np
|
|
20
|
+
|
|
21
|
+
from physicskit.particle.kinematics import FourVector, boost_generic
|
|
22
|
+
|
|
23
|
+
__all__ = [
|
|
24
|
+
"two_body_decay_momentum",
|
|
25
|
+
"two_body_decay",
|
|
26
|
+
"decay_constant",
|
|
27
|
+
"half_life",
|
|
28
|
+
"radioactive_decay_number",
|
|
29
|
+
"activity",
|
|
30
|
+
"bateman_decay_chain",
|
|
31
|
+
"michel_spectrum",
|
|
32
|
+
"sample_michel_electron_energies",
|
|
33
|
+
"muon_decay_event",
|
|
34
|
+
]
|
|
35
|
+
|
|
36
|
+
|
|
37
|
+
def two_body_decay_momentum(M, m1, m2):
|
|
38
|
+
r"""Daughter momentum magnitude in a two-body decay, in the parent's rest frame.
|
|
39
|
+
|
|
40
|
+
.. math::
|
|
41
|
+
|
|
42
|
+
p^* = \frac{\sqrt{\lambda(M^2,m_1^2,m_2^2)}}{2M}, \qquad
|
|
43
|
+
\lambda(a,b,c) = a^2+b^2+c^2-2ab-2bc-2ca
|
|
44
|
+
|
|
45
|
+
Parameters
|
|
46
|
+
----------
|
|
47
|
+
M : float
|
|
48
|
+
Parent mass.
|
|
49
|
+
m1, m2 : float
|
|
50
|
+
Daughter masses.
|
|
51
|
+
|
|
52
|
+
Returns
|
|
53
|
+
-------
|
|
54
|
+
float
|
|
55
|
+
|
|
56
|
+
Raises
|
|
57
|
+
------
|
|
58
|
+
ValueError
|
|
59
|
+
If ``M < m1 + m2`` (energetically forbidden decay).
|
|
60
|
+
|
|
61
|
+
Examples
|
|
62
|
+
--------
|
|
63
|
+
>>> round(two_body_decay_momentum(1.0, 0.4, 0.4), 6)
|
|
64
|
+
0.3
|
|
65
|
+
"""
|
|
66
|
+
if M < m1 + m2:
|
|
67
|
+
raise ValueError(f"M={M} must be >= m1+m2={m1 + m2} for the decay to be allowed.")
|
|
68
|
+
a, b, c = M**2, m1**2, m2**2
|
|
69
|
+
lam = a**2 + b**2 + c**2 - 2 * a * b - 2 * b * c - 2 * c * a
|
|
70
|
+
return float(np.sqrt(max(lam, 0.0)) / (2.0 * M))
|
|
71
|
+
|
|
72
|
+
|
|
73
|
+
def two_body_decay(M, m1, m2, cos_theta, phi):
|
|
74
|
+
"""The two daughters' four-momenta in the parent's rest frame.
|
|
75
|
+
|
|
76
|
+
Parameters
|
|
77
|
+
----------
|
|
78
|
+
M : float
|
|
79
|
+
Parent mass.
|
|
80
|
+
m1, m2 : float
|
|
81
|
+
Daughter masses.
|
|
82
|
+
cos_theta : float
|
|
83
|
+
Cosine of daughter 1's polar angle from the z-axis.
|
|
84
|
+
phi : float
|
|
85
|
+
Daughter 1's azimuthal angle.
|
|
86
|
+
|
|
87
|
+
Returns
|
|
88
|
+
-------
|
|
89
|
+
p1, p2 : FourVector
|
|
90
|
+
The two daughters, back-to-back in the parent's rest frame.
|
|
91
|
+
|
|
92
|
+
Examples
|
|
93
|
+
--------
|
|
94
|
+
>>> p1, p2 = two_body_decay(1.0, 0.4, 0.4, cos_theta=1.0, phi=0.0)
|
|
95
|
+
>>> round(p1.E, 6), round(p1.pz, 6)
|
|
96
|
+
(0.5, 0.3)
|
|
97
|
+
"""
|
|
98
|
+
p_star = two_body_decay_momentum(M, m1, m2)
|
|
99
|
+
sin_theta = np.sqrt(max(1.0 - cos_theta**2, 0.0))
|
|
100
|
+
px = p_star * sin_theta * np.cos(phi)
|
|
101
|
+
py = p_star * sin_theta * np.sin(phi)
|
|
102
|
+
pz = p_star * cos_theta
|
|
103
|
+
E1 = np.sqrt(p_star**2 + m1**2)
|
|
104
|
+
E2 = np.sqrt(p_star**2 + m2**2)
|
|
105
|
+
p1 = FourVector(float(E1), float(px), float(py), float(pz))
|
|
106
|
+
p2 = FourVector(float(E2), float(-px), float(-py), float(-pz))
|
|
107
|
+
return p1, p2
|
|
108
|
+
|
|
109
|
+
|
|
110
|
+
def decay_constant(half_life_):
|
|
111
|
+
r"""Decay constant from half-life, :math:`\lambda=\ln2/t_{1/2}`.
|
|
112
|
+
|
|
113
|
+
Examples
|
|
114
|
+
--------
|
|
115
|
+
>>> round(decay_constant(np.log(2)), 6)
|
|
116
|
+
1.0
|
|
117
|
+
"""
|
|
118
|
+
return float(np.log(2.0) / half_life_)
|
|
119
|
+
|
|
120
|
+
|
|
121
|
+
def half_life(decay_constant_):
|
|
122
|
+
r"""Half-life from decay constant, :math:`t_{1/2}=\ln2/\lambda`.
|
|
123
|
+
|
|
124
|
+
Examples
|
|
125
|
+
--------
|
|
126
|
+
>>> round(half_life(1.0), 6)
|
|
127
|
+
0.693147
|
|
128
|
+
"""
|
|
129
|
+
return float(np.log(2.0) / decay_constant_)
|
|
130
|
+
|
|
131
|
+
|
|
132
|
+
def radioactive_decay_number(N0, decay_constant_, t):
|
|
133
|
+
r"""Surviving population, :math:`N(t)=N_0e^{-\lambda t}`.
|
|
134
|
+
|
|
135
|
+
Parameters
|
|
136
|
+
----------
|
|
137
|
+
N0 : float
|
|
138
|
+
Initial population.
|
|
139
|
+
decay_constant_ : float
|
|
140
|
+
Decay constant :math:`\lambda`.
|
|
141
|
+
t : array_like
|
|
142
|
+
Time(s), same units as :math:`1/\lambda`.
|
|
143
|
+
|
|
144
|
+
Returns
|
|
145
|
+
-------
|
|
146
|
+
ndarray or float
|
|
147
|
+
|
|
148
|
+
Examples
|
|
149
|
+
--------
|
|
150
|
+
>>> round(float(radioactive_decay_number(100.0, 1.0, 0.693147)), 4)
|
|
151
|
+
50.0
|
|
152
|
+
"""
|
|
153
|
+
return N0 * np.exp(-decay_constant_ * np.asarray(t))
|
|
154
|
+
|
|
155
|
+
|
|
156
|
+
def activity(N, decay_constant_):
|
|
157
|
+
r"""Decay rate (activity), :math:`A=\lambda N`.
|
|
158
|
+
|
|
159
|
+
Examples
|
|
160
|
+
--------
|
|
161
|
+
>>> activity(100.0, 0.01)
|
|
162
|
+
1.0
|
|
163
|
+
"""
|
|
164
|
+
return decay_constant_ * N
|
|
165
|
+
|
|
166
|
+
|
|
167
|
+
def bateman_decay_chain(N0, decay_constants, t):
|
|
168
|
+
r"""Population of every species in a linear radioactive decay chain.
|
|
169
|
+
|
|
170
|
+
Solves the Bateman equations for a chain :math:`1\to2\to\cdots\to n`
|
|
171
|
+
with decay constants ``decay_constants`` (species 1 starts with
|
|
172
|
+
population ``N0``, all daughters start at zero):
|
|
173
|
+
|
|
174
|
+
.. math::
|
|
175
|
+
|
|
176
|
+
N_k(t) = N_0\Big(\prod_{i=1}^{k-1}\lambda_i\Big)
|
|
177
|
+
\sum_{i=1}^{k}\frac{e^{-\lambda_i t}}
|
|
178
|
+
{\prod_{j=1,j\neq i}^{k}(\lambda_j-\lambda_i)}
|
|
179
|
+
|
|
180
|
+
with :math:`N_1(t)=N_0e^{-\lambda_1 t}`. A zero decay constant for the
|
|
181
|
+
final species represents a stable end product.
|
|
182
|
+
|
|
183
|
+
Parameters
|
|
184
|
+
----------
|
|
185
|
+
N0 : float
|
|
186
|
+
Initial population of species 1.
|
|
187
|
+
decay_constants : sequence of float
|
|
188
|
+
Decay constant of each of the ``n`` species in the chain. Must be
|
|
189
|
+
pairwise distinct among the species actually populated (the
|
|
190
|
+
closed-form sum divides by ``lambda_j - lambda_i``).
|
|
191
|
+
t : array_like
|
|
192
|
+
Times at which to evaluate the populations.
|
|
193
|
+
|
|
194
|
+
Returns
|
|
195
|
+
-------
|
|
196
|
+
ndarray of shape (n, len(t))
|
|
197
|
+
Population of each species over time.
|
|
198
|
+
|
|
199
|
+
Examples
|
|
200
|
+
--------
|
|
201
|
+
>>> t = np.array([0.0, 1.0])
|
|
202
|
+
>>> N = bateman_decay_chain(100.0, [1.0, 2.0], t)
|
|
203
|
+
>>> N.shape
|
|
204
|
+
(2, 2)
|
|
205
|
+
>>> round(float(N[0, 0]), 6)
|
|
206
|
+
100.0
|
|
207
|
+
"""
|
|
208
|
+
t = np.asarray(t, dtype=float)
|
|
209
|
+
lam = np.asarray(decay_constants, dtype=float)
|
|
210
|
+
n = len(lam)
|
|
211
|
+
N = np.zeros((n, len(t)))
|
|
212
|
+
for k in range(n): # k is 0-indexed species k+1
|
|
213
|
+
prefactor = N0 * np.prod(lam[:k]) if k > 0 else N0
|
|
214
|
+
total = np.zeros_like(t)
|
|
215
|
+
for i in range(k + 1):
|
|
216
|
+
denom = 1.0
|
|
217
|
+
for j in range(k + 1):
|
|
218
|
+
if j != i:
|
|
219
|
+
denom *= lam[j] - lam[i]
|
|
220
|
+
total += np.exp(-lam[i] * t) / denom
|
|
221
|
+
N[k] = prefactor * total
|
|
222
|
+
return N
|
|
223
|
+
|
|
224
|
+
|
|
225
|
+
def michel_spectrum(x):
|
|
226
|
+
r"""The (unpolarized, massless-electron) Michel spectrum shape for muon decay.
|
|
227
|
+
|
|
228
|
+
.. math::
|
|
229
|
+
|
|
230
|
+
\frac{d\Gamma}{dx} = 2x^2(3-2x), \qquad x=\frac{2E_e}{m_\mu}\in[0,1]
|
|
231
|
+
|
|
232
|
+
the standard leading-order result for :math:`\mu^-\to e^-\bar\nu_\mu\nu_e`
|
|
233
|
+
from the V-A four-fermion weak interaction (Michel 1950; see e.g.
|
|
234
|
+
Commins & Bucksbaum, *Weak Interactions of Leptons and Quarks*, Ch. 4,
|
|
235
|
+
or the muon-decay chapter of any standard particle physics text),
|
|
236
|
+
in the limit :math:`m_e/m_\mu\to0` and for an unpolarized muon (no
|
|
237
|
+
Michel parameter :math:`\rho,\eta,\xi,\delta` dependence -- those
|
|
238
|
+
parametrize corrections from polarization and a nonzero electron
|
|
239
|
+
mass/anomalous couplings, all set to their V-A/Standard-Model,
|
|
240
|
+
unpolarized values here). Normalized so that :math:`\int_0^1
|
|
241
|
+
(d\Gamma/dx)\,dx = 1`.
|
|
242
|
+
|
|
243
|
+
Parameters
|
|
244
|
+
----------
|
|
245
|
+
x : array_like
|
|
246
|
+
Scaled electron energy, :math:`x=2E_e/m_\mu\in[0,1]`.
|
|
247
|
+
|
|
248
|
+
Returns
|
|
249
|
+
-------
|
|
250
|
+
ndarray or float
|
|
251
|
+
|
|
252
|
+
Examples
|
|
253
|
+
--------
|
|
254
|
+
>>> import numpy as np
|
|
255
|
+
>>> x = np.linspace(0, 1, 100001)
|
|
256
|
+
>>> round(float(np.trapezoid(michel_spectrum(x), x)), 4)
|
|
257
|
+
1.0
|
|
258
|
+
"""
|
|
259
|
+
x = np.asarray(x, dtype=float)
|
|
260
|
+
return 2.0 * x**2 * (3.0 - 2.0 * x)
|
|
261
|
+
|
|
262
|
+
|
|
263
|
+
def sample_michel_electron_energies(n, rng=None):
|
|
264
|
+
r"""Sample ``n`` scaled electron energies :math:`x=2E_e/m_\mu` from the Michel spectrum.
|
|
265
|
+
|
|
266
|
+
Rejection sampling against the shape's bound: :math:`x^2(3-2x)\le1`
|
|
267
|
+
on :math:`[0,1]` (attained at :math:`x=1`), so a uniform proposal on
|
|
268
|
+
:math:`[0,1]\times[0,1]` accepted below the (unnormalized) curve
|
|
269
|
+
:math:`x^2(3-2x)` reproduces :func:`michel_spectrum`.
|
|
270
|
+
|
|
271
|
+
Parameters
|
|
272
|
+
----------
|
|
273
|
+
n : int
|
|
274
|
+
Number of samples.
|
|
275
|
+
rng : numpy.random.Generator, optional
|
|
276
|
+
Random number generator; a fresh default one is used if omitted.
|
|
277
|
+
|
|
278
|
+
Returns
|
|
279
|
+
-------
|
|
280
|
+
ndarray of shape (n,)
|
|
281
|
+
|
|
282
|
+
Examples
|
|
283
|
+
--------
|
|
284
|
+
>>> rng = np.random.default_rng(0)
|
|
285
|
+
>>> xs = sample_michel_electron_energies(20000, rng=rng)
|
|
286
|
+
>>> bool(0.68 < xs.mean() < 0.72) # theoretical mean <x> = 7/10
|
|
287
|
+
True
|
|
288
|
+
"""
|
|
289
|
+
rng = np.random.default_rng() if rng is None else rng
|
|
290
|
+
samples = np.empty(n)
|
|
291
|
+
filled = 0
|
|
292
|
+
while filled < n:
|
|
293
|
+
batch = max(2 * (n - filled), 16)
|
|
294
|
+
x_cand = rng.uniform(0.0, 1.0, size=batch)
|
|
295
|
+
y_cand = rng.uniform(0.0, 1.0, size=batch)
|
|
296
|
+
accepted = x_cand[y_cand <= x_cand**2 * (3.0 - 2.0 * x_cand)]
|
|
297
|
+
take = accepted[: n - filled]
|
|
298
|
+
samples[filled : filled + len(take)] = take
|
|
299
|
+
filled += len(take)
|
|
300
|
+
return samples
|
|
301
|
+
|
|
302
|
+
|
|
303
|
+
def muon_decay_event(m_mu, rng=None):
|
|
304
|
+
r"""Sample one :math:`\mu^-\to e^-+\bar\nu_\mu+\nu_e` decay in the muon rest frame.
|
|
305
|
+
|
|
306
|
+
Toy-but-exact three-body kinematics built from two chained exact
|
|
307
|
+
two-body decays (reusing :func:`two_body_decay`, so energy-momentum
|
|
308
|
+
is conserved to machine precision at both vertices):
|
|
309
|
+
|
|
310
|
+
1. The electron's energy is drawn from the Michel spectrum (massless
|
|
311
|
+
electron approximation) via :func:`sample_michel_electron_energies`,
|
|
312
|
+
fixing the invariant mass of the recoiling neutrino pair through
|
|
313
|
+
:math:`m_{\nu\nu}^2=m_\mu^2-2m_\mu E_e` (exact for :math:`m_e=0`).
|
|
314
|
+
:func:`two_body_decay` then gives the electron and the
|
|
315
|
+
neutrino-pair "system" four-momenta, back to back in the muon
|
|
316
|
+
rest frame, with an isotropically sampled decay angle (the
|
|
317
|
+
standard unpolarized-muon assumption).
|
|
318
|
+
2. The neutrino-pair system is split into its two (massless)
|
|
319
|
+
neutrinos isotropically in *its own* rest frame via a second call
|
|
320
|
+
to :func:`two_body_decay`, then boosted back to the muon rest
|
|
321
|
+
frame with :func:`~physicskit.particle.kinematics.boost_generic`.
|
|
322
|
+
|
|
323
|
+
Both neutrino masses are set to zero -- an excellent approximation
|
|
324
|
+
given their sub-eV masses compared to :math:`m_\mu\sim100` MeV.
|
|
325
|
+
|
|
326
|
+
Parameters
|
|
327
|
+
----------
|
|
328
|
+
m_mu : float
|
|
329
|
+
Muon mass (in whatever energy unit the caller uses consistently).
|
|
330
|
+
rng : numpy.random.Generator, optional
|
|
331
|
+
Random number generator; a fresh default one is used if omitted.
|
|
332
|
+
|
|
333
|
+
Returns
|
|
334
|
+
-------
|
|
335
|
+
p_e, p_numu_bar, p_nue : FourVector
|
|
336
|
+
The three decay products, in the muon rest frame.
|
|
337
|
+
|
|
338
|
+
Examples
|
|
339
|
+
--------
|
|
340
|
+
>>> from physicskit.particle.kinematics import invariant_mass
|
|
341
|
+
>>> rng = np.random.default_rng(1)
|
|
342
|
+
>>> p_e, p_numu_bar, p_nue = muon_decay_event(105.658, rng=rng)
|
|
343
|
+
>>> round(invariant_mass([p_e, p_numu_bar, p_nue]), 6)
|
|
344
|
+
105.658
|
|
345
|
+
"""
|
|
346
|
+
rng = np.random.default_rng() if rng is None else rng
|
|
347
|
+
x = float(sample_michel_electron_energies(1, rng=rng)[0])
|
|
348
|
+
E_e = 0.5 * x * m_mu
|
|
349
|
+
m_nunu = float(np.sqrt(max(m_mu**2 - 2.0 * m_mu * E_e, 0.0)))
|
|
350
|
+
cos1, phi1 = rng.uniform(-1.0, 1.0), rng.uniform(0.0, 2.0 * np.pi)
|
|
351
|
+
p_e, p_nunu = two_body_decay(m_mu, 0.0, m_nunu, cos1, phi1)
|
|
352
|
+
cos2, phi2 = rng.uniform(-1.0, 1.0), rng.uniform(0.0, 2.0 * np.pi)
|
|
353
|
+
p_numu_bar_rest, p_nue_rest = two_body_decay(m_nunu, 0.0, 0.0, cos2, phi2)
|
|
354
|
+
beta_vec = p_nunu.p_vec / p_nunu.E
|
|
355
|
+
p_numu_bar = boost_generic(p_numu_bar_rest, beta_vec)
|
|
356
|
+
p_nue = boost_generic(p_nue_rest, beta_vec)
|
|
357
|
+
return p_e, p_numu_bar, p_nue
|
|
@@ -0,0 +1,300 @@
|
|
|
1
|
+
r"""Toy models of three electroweak/QED phenomena: spontaneous symmetry
|
|
2
|
+
breaking, leading-order QED annihilation, and neutral-meson CP violation.
|
|
3
|
+
|
|
4
|
+
Uses the same natural-unit convention (:math:`\hbar=c=1`) as
|
|
5
|
+
:mod:`physicskit.particle.kinematics`.
|
|
6
|
+
|
|
7
|
+
- :func:`higgs_potential`, :func:`higgs_vev`, :func:`higgs_field_rollover`
|
|
8
|
+
-- classical spontaneous symmetry breaking of a real scalar field in a
|
|
9
|
+
:math:`\phi^4` double-well potential (the same mechanism underlying
|
|
10
|
+
the Higgs field's nonzero vacuum expectation value), reduced to a
|
|
11
|
+
single spatial point (0+1 dimensional) for simplicity.
|
|
12
|
+
- :func:`qed_dsigma_domega_mumu`, :func:`qed_total_cross_section_mumu` --
|
|
13
|
+
the leading-order (tree-level, single-photon-exchange) QED
|
|
14
|
+
differential and total cross sections for :math:`e^+e^-\to\mu^+\mu^-`.
|
|
15
|
+
- :func:`meson_decay_rates_cp_eigenstate`, :func:`cp_asymmetry` -- a
|
|
16
|
+
Wigner-Weisskopf two-state-mixing toy model of neutral-meson
|
|
17
|
+
(:math:`K^0`-:math:`\bar K^0`-style) CP violation in the decay-rate
|
|
18
|
+
asymmetry to a common CP eigenstate final state.
|
|
19
|
+
"""
|
|
20
|
+
|
|
21
|
+
from __future__ import annotations
|
|
22
|
+
|
|
23
|
+
import numpy as np
|
|
24
|
+
from scipy.integrate import solve_ivp
|
|
25
|
+
|
|
26
|
+
from physicskit.particle.scattering import ALPHA_FS
|
|
27
|
+
|
|
28
|
+
__all__ = [
|
|
29
|
+
"higgs_potential",
|
|
30
|
+
"higgs_vev",
|
|
31
|
+
"higgs_field_rollover",
|
|
32
|
+
"qed_dsigma_domega_mumu",
|
|
33
|
+
"qed_total_cross_section_mumu",
|
|
34
|
+
"meson_decay_rates_cp_eigenstate",
|
|
35
|
+
"cp_asymmetry",
|
|
36
|
+
]
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
def higgs_potential(phi, a, b):
|
|
40
|
+
r"""The classical :math:`\phi^4` double-well potential, :math:`V(\phi)=-a\phi^2+b\phi^4`.
|
|
41
|
+
|
|
42
|
+
For :math:`a,b>0` this has an unstable extremum at :math:`\phi=0`
|
|
43
|
+
(the symmetric, "false vacuum" point) and two degenerate true minima
|
|
44
|
+
at :math:`\phi=\pm v`, :math:`v=\sqrt{a/(2b)}` -- the field must
|
|
45
|
+
"choose" one of them, spontaneously breaking the :math:`\phi\to-\phi`
|
|
46
|
+
symmetry. This is the same quartic potential that gives the Higgs
|
|
47
|
+
field its nonzero vacuum expectation value.
|
|
48
|
+
|
|
49
|
+
Parameters
|
|
50
|
+
----------
|
|
51
|
+
phi : array_like
|
|
52
|
+
Field value.
|
|
53
|
+
a, b : float
|
|
54
|
+
Potential parameters, :math:`a,b>0`.
|
|
55
|
+
|
|
56
|
+
Returns
|
|
57
|
+
-------
|
|
58
|
+
ndarray or float
|
|
59
|
+
|
|
60
|
+
Examples
|
|
61
|
+
--------
|
|
62
|
+
>>> float(higgs_potential(0.0, a=1.0, b=1.0))
|
|
63
|
+
0.0
|
|
64
|
+
"""
|
|
65
|
+
phi = np.asarray(phi, dtype=float)
|
|
66
|
+
return -a * phi**2 + b * phi**4
|
|
67
|
+
|
|
68
|
+
|
|
69
|
+
def higgs_vev(a, b):
|
|
70
|
+
r"""The true-vacuum field value, :math:`v=\sqrt{a/(2b)}`, minimizing :func:`higgs_potential`.
|
|
71
|
+
|
|
72
|
+
Examples
|
|
73
|
+
--------
|
|
74
|
+
>>> round(higgs_vev(a=2.0, b=1.0), 6)
|
|
75
|
+
1.0
|
|
76
|
+
"""
|
|
77
|
+
return float(np.sqrt(a / (2.0 * b)))
|
|
78
|
+
|
|
79
|
+
|
|
80
|
+
def higgs_field_rollover(phi0, phidot0, a, b, t_eval, damping=0.0):
|
|
81
|
+
r"""Classically evolve a homogeneous scalar field rolling in :func:`higgs_potential`.
|
|
82
|
+
|
|
83
|
+
Integrates the (0+1 dimensional -- no spatial gradient/kink
|
|
84
|
+
structure, a single point standing in for a spatially uniform field
|
|
85
|
+
configuration) classical field equation
|
|
86
|
+
|
|
87
|
+
.. math::
|
|
88
|
+
|
|
89
|
+
\ddot\phi = -\frac{dV}{d\phi} - \gamma\dot\phi
|
|
90
|
+
= 2a\phi - 4b\phi^3 - \gamma\dot\phi
|
|
91
|
+
|
|
92
|
+
Started near the unstable symmetric point :math:`\phi\approx0` with
|
|
93
|
+
a tiny perturbation, the field is repelled from it and rolls down
|
|
94
|
+
into one of the two true vacua :math:`\phi=\pm v`
|
|
95
|
+
(:func:`higgs_vev`) -- whichever side the initial perturbation
|
|
96
|
+
pushes it toward, a toy realization of spontaneous symmetry
|
|
97
|
+
breaking. A small damping :math:`\gamma>0` (representing energy
|
|
98
|
+
radiated into other field modes, not modeled explicitly) lets the
|
|
99
|
+
field settle into the chosen vacuum instead of oscillating in it
|
|
100
|
+
forever.
|
|
101
|
+
|
|
102
|
+
Parameters
|
|
103
|
+
----------
|
|
104
|
+
phi0, phidot0 : float
|
|
105
|
+
Initial field value and velocity.
|
|
106
|
+
a, b : float
|
|
107
|
+
Potential parameters, see :func:`higgs_potential`.
|
|
108
|
+
t_eval : array_like
|
|
109
|
+
Times at which to report the solution.
|
|
110
|
+
damping : float, default=0.0
|
|
111
|
+
Damping coefficient :math:`\gamma\ge0`.
|
|
112
|
+
|
|
113
|
+
Returns
|
|
114
|
+
-------
|
|
115
|
+
phi, phidot : ndarray
|
|
116
|
+
Field value and velocity at each time in ``t_eval``.
|
|
117
|
+
|
|
118
|
+
Examples
|
|
119
|
+
--------
|
|
120
|
+
>>> import numpy as np
|
|
121
|
+
>>> t = np.linspace(0, 60, 600)
|
|
122
|
+
>>> phi, phidot = higgs_field_rollover(1e-3, 0.0, a=1.0, b=1.0, t_eval=t, damping=0.08)
|
|
123
|
+
>>> v = higgs_vev(1.0, 1.0)
|
|
124
|
+
>>> bool(abs(abs(phi[-1]) - v) < 0.05)
|
|
125
|
+
True
|
|
126
|
+
"""
|
|
127
|
+
t_eval = np.asarray(t_eval, dtype=float)
|
|
128
|
+
|
|
129
|
+
def rhs(t, y):
|
|
130
|
+
phi, phidot = y
|
|
131
|
+
return [phidot, 2.0 * a * phi - 4.0 * b * phi**3 - damping * phidot]
|
|
132
|
+
|
|
133
|
+
sol = solve_ivp(rhs, (t_eval[0], t_eval[-1]), [phi0, phidot0], t_eval=t_eval, rtol=1e-9, atol=1e-12)
|
|
134
|
+
return sol.y[0], sol.y[1]
|
|
135
|
+
|
|
136
|
+
|
|
137
|
+
def qed_dsigma_domega_mumu(cos_theta, sqrt_s, alpha=ALPHA_FS):
|
|
138
|
+
r"""Leading-order QED differential cross section for :math:`e^+e^-\to\mu^+\mu^-`.
|
|
139
|
+
|
|
140
|
+
.. math::
|
|
141
|
+
|
|
142
|
+
\frac{d\sigma}{d\Omega} = \frac{\alpha^2}{4s}\left(1+\cos^2\theta\right)
|
|
143
|
+
|
|
144
|
+
the standard tree-level, single-photon-exchange, unpolarized result
|
|
145
|
+
in the ultrarelativistic (massless-fermion) limit -- e.g. Peskin &
|
|
146
|
+
Schroeder, *An Introduction to Quantum Field Theory*, eq. (5.15); or
|
|
147
|
+
Halzen & Martin, *Quarks and Leptons*, eq. (6.23). :math:`\theta` is
|
|
148
|
+
the muon's polar angle relative to the beam in the center-of-mass
|
|
149
|
+
frame, and :math:`s=(\sqrt s)^2` is the Mandelstam invariant (see
|
|
150
|
+
:func:`physicskit.particle.scattering.mandelstam_s`).
|
|
151
|
+
|
|
152
|
+
**Simplification**: electron and muon masses are neglected (valid
|
|
153
|
+
for :math:`\sqrt s\gg2m_\mu\approx0.2` GeV); higher-order QED
|
|
154
|
+
corrections and any :math:`Z`-boson contribution (relevant near and
|
|
155
|
+
above the :math:`Z` pole, :math:`\sqrt s\sim91` GeV) are not included.
|
|
156
|
+
|
|
157
|
+
Parameters
|
|
158
|
+
----------
|
|
159
|
+
cos_theta : array_like
|
|
160
|
+
Cosine of the muon's center-of-mass polar angle.
|
|
161
|
+
sqrt_s : float
|
|
162
|
+
Center-of-mass energy.
|
|
163
|
+
alpha : float, default=ALPHA_FS
|
|
164
|
+
Fine-structure constant.
|
|
165
|
+
|
|
166
|
+
Returns
|
|
167
|
+
-------
|
|
168
|
+
ndarray or float
|
|
169
|
+
|
|
170
|
+
Examples
|
|
171
|
+
--------
|
|
172
|
+
>>> round(float(qed_dsigma_domega_mumu(0.0, sqrt_s=10.0) / qed_dsigma_domega_mumu(1.0, sqrt_s=10.0)), 6)
|
|
173
|
+
0.5
|
|
174
|
+
"""
|
|
175
|
+
cos_theta = np.asarray(cos_theta, dtype=float)
|
|
176
|
+
s = sqrt_s**2
|
|
177
|
+
return (alpha**2 / (4.0 * s)) * (1.0 + cos_theta**2)
|
|
178
|
+
|
|
179
|
+
|
|
180
|
+
def qed_total_cross_section_mumu(sqrt_s, alpha=ALPHA_FS):
|
|
181
|
+
r"""Total leading-order QED cross section for :math:`e^+e^-\to\mu^+\mu^-`.
|
|
182
|
+
|
|
183
|
+
.. math::
|
|
184
|
+
|
|
185
|
+
\sigma = \frac{4\pi\alpha^2}{3s}
|
|
186
|
+
|
|
187
|
+
obtained by integrating :func:`qed_dsigma_domega_mumu` over the full
|
|
188
|
+
solid angle; the same simplifications apply (massless fermions, no
|
|
189
|
+
:math:`Z` contribution).
|
|
190
|
+
|
|
191
|
+
Parameters
|
|
192
|
+
----------
|
|
193
|
+
sqrt_s : float
|
|
194
|
+
Center-of-mass energy.
|
|
195
|
+
alpha : float, default=ALPHA_FS
|
|
196
|
+
Fine-structure constant.
|
|
197
|
+
|
|
198
|
+
Returns
|
|
199
|
+
-------
|
|
200
|
+
float
|
|
201
|
+
|
|
202
|
+
Examples
|
|
203
|
+
--------
|
|
204
|
+
>>> round(qed_total_cross_section_mumu(10.0), 10) == round(4 * np.pi * ALPHA_FS**2 / (3 * 100.0), 10)
|
|
205
|
+
True
|
|
206
|
+
"""
|
|
207
|
+
s = sqrt_s**2
|
|
208
|
+
return 4.0 * np.pi * alpha**2 / (3.0 * s)
|
|
209
|
+
|
|
210
|
+
|
|
211
|
+
def meson_decay_rates_cp_eigenstate(t, delta_m, gamma_s, gamma_l, epsilon):
|
|
212
|
+
r"""Time-dependent :math:`P^0,\bar P^0\to f_{CP}` decay rates, Wigner-Weisskopf toy model.
|
|
213
|
+
|
|
214
|
+
A neutral meson :math:`P^0` (modeled on the :math:`K^0`-:math:`\bar
|
|
215
|
+
K^0` system) mixes through the effective non-Hermitian Hamiltonian
|
|
216
|
+
:math:`H=M-i\Gamma/2`; its mass eigenstates are the short/long-lived
|
|
217
|
+
combinations :math:`P_{S,L}\approx P^0\pm\bar P^0` (up to the small
|
|
218
|
+
CP-violating admixture parametrized by the complex parameter
|
|
219
|
+
:math:`\varepsilon`, :math:`|\varepsilon|\ll1`). Decaying to a common
|
|
220
|
+
CP eigenstate final state :math:`f` (e.g. :math:`\pi^+\pi^-`), the
|
|
221
|
+
two flavor-tagged rates interfere as
|
|
222
|
+
|
|
223
|
+
.. math::
|
|
224
|
+
|
|
225
|
+
\Gamma(P^0(t)\to f) &= e^{-\Gamma_S t} + |\varepsilon|^2e^{-\Gamma_L t}
|
|
226
|
+
+ 2|\varepsilon|e^{-\Gamma t}\cos(\Delta m\,t-\phi_\varepsilon) \\
|
|
227
|
+
\Gamma(\bar P^0(t)\to f) &= e^{-\Gamma_S t} + |\varepsilon|^2e^{-\Gamma_L t}
|
|
228
|
+
- 2|\varepsilon|e^{-\Gamma t}\cos(\Delta m\,t-\phi_\varepsilon)
|
|
229
|
+
|
|
230
|
+
with :math:`\Gamma=(\Gamma_S+\Gamma_L)/2`; this is the standard
|
|
231
|
+
interference pattern used to measure :math:`\Delta m` and the
|
|
232
|
+
:math:`K_S` lifetime from :math:`K^0/\bar K^0\to\pi\pi` decay-rate
|
|
233
|
+
oscillations (see the Particle Data Group's "CP violation in
|
|
234
|
+
:math:`K_L` decays" review, or Griffiths, *Introduction to Elementary
|
|
235
|
+
Particles*, Ch. 8).
|
|
236
|
+
|
|
237
|
+
Parameters
|
|
238
|
+
----------
|
|
239
|
+
t : array_like
|
|
240
|
+
Proper time since production (tagged as a pure :math:`P^0` or
|
|
241
|
+
:math:`\bar P^0` flavor eigenstate at :math:`t=0`).
|
|
242
|
+
delta_m : float
|
|
243
|
+
Mass splitting between the two mass eigenstates, :math:`\Delta m=m_L-m_S`.
|
|
244
|
+
gamma_s, gamma_l : float
|
|
245
|
+
Decay widths of the short- and long-lived mass eigenstates.
|
|
246
|
+
epsilon : complex
|
|
247
|
+
CP-violation parameter, :math:`|\varepsilon|\ll1`.
|
|
248
|
+
|
|
249
|
+
Returns
|
|
250
|
+
-------
|
|
251
|
+
gamma_meson, gamma_mesonbar : ndarray
|
|
252
|
+
|
|
253
|
+
Examples
|
|
254
|
+
--------
|
|
255
|
+
>>> import numpy as np
|
|
256
|
+
>>> t = np.linspace(0, 5, 6)
|
|
257
|
+
>>> g, gbar = meson_decay_rates_cp_eigenstate(t, delta_m=1.0, gamma_s=5.0, gamma_l=0.5, epsilon=0.0)
|
|
258
|
+
>>> np.allclose(g, gbar)
|
|
259
|
+
True
|
|
260
|
+
"""
|
|
261
|
+
t = np.asarray(t, dtype=float)
|
|
262
|
+
eps = complex(epsilon)
|
|
263
|
+
eps_abs, phi_eps = abs(eps), np.angle(eps)
|
|
264
|
+
gamma = 0.5 * (gamma_s + gamma_l)
|
|
265
|
+
common = np.exp(-gamma_s * t) + eps_abs**2 * np.exp(-gamma_l * t)
|
|
266
|
+
osc = 2.0 * eps_abs * np.exp(-gamma * t) * np.cos(delta_m * t - phi_eps)
|
|
267
|
+
return common + osc, common - osc
|
|
268
|
+
|
|
269
|
+
|
|
270
|
+
def cp_asymmetry(t, delta_m, gamma_s, gamma_l, epsilon):
|
|
271
|
+
r"""Decay-rate CP asymmetry :math:`A(t)`, from :func:`meson_decay_rates_cp_eigenstate`.
|
|
272
|
+
|
|
273
|
+
.. math::
|
|
274
|
+
|
|
275
|
+
A(t) = \frac{\Gamma(\bar P^0(t)\to f) - \Gamma(P^0(t)\to f)}
|
|
276
|
+
{\Gamma(\bar P^0(t)\to f) + \Gamma(P^0(t)\to f)}
|
|
277
|
+
|
|
278
|
+
which oscillates at frequency :math:`\Delta m` inside a decaying
|
|
279
|
+
envelope, vanishing identically for :math:`\varepsilon=0` (no CP
|
|
280
|
+
violation).
|
|
281
|
+
|
|
282
|
+
Parameters
|
|
283
|
+
----------
|
|
284
|
+
t, delta_m, gamma_s, gamma_l, epsilon
|
|
285
|
+
See :func:`meson_decay_rates_cp_eigenstate`.
|
|
286
|
+
|
|
287
|
+
Returns
|
|
288
|
+
-------
|
|
289
|
+
ndarray or float
|
|
290
|
+
|
|
291
|
+
Examples
|
|
292
|
+
--------
|
|
293
|
+
>>> import numpy as np
|
|
294
|
+
>>> t = np.linspace(0, 5, 6)
|
|
295
|
+
>>> A = cp_asymmetry(t, delta_m=1.0, gamma_s=5.0, gamma_l=0.5, epsilon=0.0)
|
|
296
|
+
>>> np.allclose(A, 0.0)
|
|
297
|
+
True
|
|
298
|
+
"""
|
|
299
|
+
gamma_meson, gamma_mesonbar = meson_decay_rates_cp_eigenstate(t, delta_m, gamma_s, gamma_l, epsilon)
|
|
300
|
+
return (gamma_mesonbar - gamma_meson) / (gamma_mesonbar + gamma_meson)
|