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,151 @@
|
|
|
1
|
+
"""Landau's phenomenological theory of continuous phase transitions.
|
|
2
|
+
|
|
3
|
+
Rather than derive a phase transition from microscopic interactions, Landau
|
|
4
|
+
(1937) asked what the *free energy itself* must look like, given only the
|
|
5
|
+
symmetry of the order parameter, near a continuous transition. For an
|
|
6
|
+
order parameter :math:`m` (magnetization, density difference, ...) that
|
|
7
|
+
the disordered phase's symmetry forbids from appearing at odd order, the
|
|
8
|
+
simplest possible expansion is
|
|
9
|
+
|
|
10
|
+
.. math::
|
|
11
|
+
|
|
12
|
+
F(m, T) = a(T - T_C)\\, m^2 + b\\, m^4 - h\\, m, \\qquad a, b > 0,
|
|
13
|
+
|
|
14
|
+
with an external field :math:`h` coupling linearly to :math:`m`. Minimizing
|
|
15
|
+
this quartic over :math:`m` reproduces, from symmetry and analyticity
|
|
16
|
+
alone, the qualitative shape of every continuous transition: a single
|
|
17
|
+
minimum at :math:`m = 0` above :math:`T_C`, a spontaneous, symmetry-broken
|
|
18
|
+
pair of minima :math:`m = \\pm\\sqrt{a(T_C - T)/2b}` below it, and a
|
|
19
|
+
susceptibility that diverges from both sides as :math:`T \\to T_C`. Landau
|
|
20
|
+
theory's mean-field critical exponents (:math:`\\beta = 1/2`, :math:`\\gamma
|
|
21
|
+
= 1`) are quantitatively wrong in low dimensions -- famously not matching
|
|
22
|
+
Onsager's exact 2D Ising values -- but the qualitative order-parameter
|
|
23
|
+
picture it introduced, and the idea of classifying transitions by how they
|
|
24
|
+
break symmetry, underlies the entire modern theory of phase transitions
|
|
25
|
+
that the renormalization group later completed.
|
|
26
|
+
"""
|
|
27
|
+
|
|
28
|
+
from __future__ import annotations
|
|
29
|
+
|
|
30
|
+
import numpy as np
|
|
31
|
+
|
|
32
|
+
__all__ = ["landau_equilibrium_magnetization", "landau_free_energy", "landau_susceptibility"]
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
def landau_free_energy(m, T, Tc, a=1.0, b=1.0, h=0.0):
|
|
36
|
+
"""Landau free energy :math:`F(m) = a(T - T_C) m^2 + b m^4 - h m`.
|
|
37
|
+
|
|
38
|
+
Parameters
|
|
39
|
+
----------
|
|
40
|
+
m : array_like
|
|
41
|
+
Order parameter value(s) at which to evaluate :math:`F`.
|
|
42
|
+
T : float
|
|
43
|
+
Temperature.
|
|
44
|
+
Tc : float
|
|
45
|
+
Critical temperature.
|
|
46
|
+
a, b : float, default=1.0
|
|
47
|
+
Positive Landau expansion coefficients.
|
|
48
|
+
h : float, default=0.0
|
|
49
|
+
External field, linearly coupled to :math:`m`.
|
|
50
|
+
|
|
51
|
+
Returns
|
|
52
|
+
-------
|
|
53
|
+
ndarray
|
|
54
|
+
"""
|
|
55
|
+
m = np.asarray(m, dtype=np.float64)
|
|
56
|
+
return a * (T - Tc) * m**2 + b * m**4 - h * m
|
|
57
|
+
|
|
58
|
+
|
|
59
|
+
def landau_equilibrium_magnetization(T, Tc, a=1.0, b=1.0, h=0.0):
|
|
60
|
+
"""Order parameter minimizing the Landau free energy at temperature T.
|
|
61
|
+
|
|
62
|
+
Solves :math:`\\partial F/\\partial m = 2a(T-T_C)m + 4bm^3 - h = 0` for
|
|
63
|
+
every real root, and returns the one with the lowest :math:`F` (the
|
|
64
|
+
true equilibrium branch, correctly following the symmetry-broken
|
|
65
|
+
minimum rather than the unstable one once :math:`h \\ne 0` tilts the
|
|
66
|
+
double well). At :math:`h = 0` below :math:`T_C` the two symmetry-broken
|
|
67
|
+
roots :math:`\\pm\\sqrt{a(T_C-T)/2b}` are exactly degenerate in
|
|
68
|
+
:math:`F`; ties are broken deterministically in favor of the
|
|
69
|
+
non-negative root (the conventional "up" branch of spontaneous symmetry
|
|
70
|
+
breaking), so that :math:`m(T)` is a single-valued, continuous curve
|
|
71
|
+
rather than jumping unpredictably between the two equally valid
|
|
72
|
+
branches as :math:`T` is swept. At :math:`h = 0` this reduces to the
|
|
73
|
+
textbook result :math:`m = 0` for :math:`T \\ge T_C` and :math:`m =
|
|
74
|
+
\\sqrt{a(T_C - T)/2b}` for :math:`T < T_C` -- the mean-field
|
|
75
|
+
:math:`\\beta = 1/2` critical exponent.
|
|
76
|
+
|
|
77
|
+
Parameters
|
|
78
|
+
----------
|
|
79
|
+
T : float or array_like
|
|
80
|
+
Temperature(s).
|
|
81
|
+
Tc : float
|
|
82
|
+
Critical temperature.
|
|
83
|
+
a, b : float, default=1.0
|
|
84
|
+
Positive Landau expansion coefficients.
|
|
85
|
+
h : float, default=0.0
|
|
86
|
+
External field.
|
|
87
|
+
|
|
88
|
+
Returns
|
|
89
|
+
-------
|
|
90
|
+
float or ndarray
|
|
91
|
+
Equilibrium order parameter, matching the shape of ``T``.
|
|
92
|
+
|
|
93
|
+
Examples
|
|
94
|
+
--------
|
|
95
|
+
>>> round(landau_equilibrium_magnetization(T=1.0, Tc=2.0, a=1.0, b=1.0, h=0.0), 6)
|
|
96
|
+
0.707107
|
|
97
|
+
>>> landau_equilibrium_magnetization(T=3.0, Tc=2.0, a=1.0, b=1.0, h=0.0)
|
|
98
|
+
0.0
|
|
99
|
+
"""
|
|
100
|
+
T_arr = np.atleast_1d(np.asarray(T, dtype=np.float64))
|
|
101
|
+
m_eq = np.empty_like(T_arr)
|
|
102
|
+
for i, Ti in enumerate(T_arr):
|
|
103
|
+
coeffs = [4.0 * b, 0.0, 2.0 * a * (Ti - Tc), -h]
|
|
104
|
+
roots = np.roots(coeffs)
|
|
105
|
+
real_roots = roots[np.abs(roots.imag) < 1e-8].real
|
|
106
|
+
F_vals = a * (Ti - Tc) * real_roots**2 + b * real_roots**4 - h * real_roots
|
|
107
|
+
# Below T_C at h=0 the +/-m branches are exactly degenerate in F, so
|
|
108
|
+
# argmin alone would tie-break on np.roots' arbitrary root ordering,
|
|
109
|
+
# flipping sign unpredictably as T is swept. Restrict to the
|
|
110
|
+
# (numerically) tied minimizers and deterministically prefer the
|
|
111
|
+
# largest (non-negative, "up"-branch) one among them.
|
|
112
|
+
is_min = F_vals <= F_vals.min() + 1e-9 * (1.0 + np.abs(F_vals.min()))
|
|
113
|
+
m_eq[i] = real_roots[is_min].max()
|
|
114
|
+
return float(m_eq[0]) if np.ndim(T) == 0 else m_eq
|
|
115
|
+
|
|
116
|
+
|
|
117
|
+
def landau_susceptibility(T, Tc, a=1.0, b=1.0):
|
|
118
|
+
"""Zero-field susceptibility :math:`\\chi = (\\partial^2 F/\\partial m^2)^{-1}` at equilibrium.
|
|
119
|
+
|
|
120
|
+
Evaluated at the :math:`h=0` equilibrium magnetization, this gives the
|
|
121
|
+
standard mean-field result
|
|
122
|
+
|
|
123
|
+
.. math::
|
|
124
|
+
|
|
125
|
+
\\chi(T) = \\begin{cases}
|
|
126
|
+
\\dfrac{1}{2a(T - T_C)}, & T > T_C, \\\\[4pt]
|
|
127
|
+
\\dfrac{1}{4a(T_C - T)}, & T < T_C,
|
|
128
|
+
\\end{cases}
|
|
129
|
+
|
|
130
|
+
diverging on both sides of :math:`T_C` with the same exponent
|
|
131
|
+
:math:`\\gamma = 1` but different amplitudes -- the universal
|
|
132
|
+
mean-field amplitude ratio of 2.
|
|
133
|
+
|
|
134
|
+
Parameters
|
|
135
|
+
----------
|
|
136
|
+
T : array_like
|
|
137
|
+
Temperature(s); may include ``Tc`` itself, where :math:`\\chi`
|
|
138
|
+
diverges (``inf`` is returned there).
|
|
139
|
+
Tc : float
|
|
140
|
+
Critical temperature.
|
|
141
|
+
a, b : float, default=1.0
|
|
142
|
+
Positive Landau expansion coefficients (``b`` is unused above
|
|
143
|
+
:math:`T_C`, kept for a uniform signature).
|
|
144
|
+
|
|
145
|
+
Returns
|
|
146
|
+
-------
|
|
147
|
+
ndarray
|
|
148
|
+
"""
|
|
149
|
+
T = np.asarray(T, dtype=np.float64)
|
|
150
|
+
with np.errstate(divide="ignore"):
|
|
151
|
+
return np.where(T > Tc, 1.0 / (2.0 * a * (T - Tc)), 1.0 / (4.0 * a * (Tc - T)))
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
"""Exact partition-function enumeration and the Lee-Yang circle theorem.
|
|
2
|
+
|
|
3
|
+
Lee and Yang (1952) asked where a phase transition -- a genuine
|
|
4
|
+
discontinuity or divergence in the free energy -- could possibly come from,
|
|
5
|
+
given that a finite system's partition function is a finite sum of
|
|
6
|
+
manifestly analytic terms. Their answer: it comes from the zeros of the
|
|
7
|
+
partition function, analytically continued into the *complex* fugacity
|
|
8
|
+
plane. For a finite ferromagnetic Ising system in a field, every such zero
|
|
9
|
+
lies exactly on the unit circle (the "Lee-Yang circle theorem"); as the
|
|
10
|
+
system size grows, these zeros multiply and crowd toward the positive real
|
|
11
|
+
axis, and a phase transition occurs exactly where, in the thermodynamic
|
|
12
|
+
limit, they pinch that axis. No finite system has a true singularity, but
|
|
13
|
+
the zeros' approach to one is visible well before that limit.
|
|
14
|
+
|
|
15
|
+
This module computes the partition function of a small Ising system
|
|
16
|
+
*exactly*, by full enumeration of every spin configuration -- feasible up to roughly
|
|
17
|
+
:math:`N \\approx 20` (:math:`2^N` configurations are enumerated
|
|
18
|
+
explicitly) -- as a polynomial in the fugacity, and finds
|
|
19
|
+
that polynomial's roots directly.
|
|
20
|
+
"""
|
|
21
|
+
|
|
22
|
+
from __future__ import annotations
|
|
23
|
+
|
|
24
|
+
import numpy as np
|
|
25
|
+
|
|
26
|
+
__all__ = ["ising_partition_polynomial", "yang_lee_zeros"]
|
|
27
|
+
|
|
28
|
+
|
|
29
|
+
def ising_partition_polynomial(N, beta, J=1.0, periodic=True):
|
|
30
|
+
"""Exact partition function of a small 1D Ising chain, as a polynomial in the fugacity.
|
|
31
|
+
|
|
32
|
+
With an external field :math:`h`, the Hamiltonian is :math:`H =
|
|
33
|
+
-J\\sum_{\\langle i,j\\rangle} s_i s_j - h \\sum_i s_i`. Writing the
|
|
34
|
+
fugacity :math:`z = e^{2\\beta h}`, the partition function factors as
|
|
35
|
+
|
|
36
|
+
.. math::
|
|
37
|
+
|
|
38
|
+
Z(\\beta, h) = e^{-\\beta h N} \\sum_{k=0}^{N} g_k\\, z^k,
|
|
39
|
+
|
|
40
|
+
where :math:`g_k = \\sum_{\\{s\\}:\\, n_\\uparrow(s) = k}
|
|
41
|
+
e^{-\\beta H_0(s)}` sums the field-free Boltzmann weight over every
|
|
42
|
+
configuration with exactly :math:`k` up-spins. The prefactor
|
|
43
|
+
:math:`e^{-\\beta h N}` is nonzero and analytic in :math:`h`, so it
|
|
44
|
+
never contributes a zero: the zeros of :math:`Z` as a function of
|
|
45
|
+
:math:`z` are exactly the roots of this polynomial's coefficients
|
|
46
|
+
``g_k``, which is all :func:`yang_lee_zeros` needs.
|
|
47
|
+
|
|
48
|
+
Every one of the :math:`2^N` configurations is enumerated directly, so
|
|
49
|
+
this is only practical for modest :math:`N` (roughly 20 at most --
|
|
50
|
+
``2**30`` configurations will exhaust memory).
|
|
51
|
+
|
|
52
|
+
Parameters
|
|
53
|
+
----------
|
|
54
|
+
N : int
|
|
55
|
+
Number of spins.
|
|
56
|
+
beta : float
|
|
57
|
+
Inverse temperature.
|
|
58
|
+
J : float, default=1.0
|
|
59
|
+
Nearest-neighbor coupling. ``J > 0`` (ferromagnetic) is the regime
|
|
60
|
+
the Lee-Yang circle theorem applies to.
|
|
61
|
+
periodic : bool, default=True
|
|
62
|
+
Periodic (ring) vs. open chain boundary conditions.
|
|
63
|
+
|
|
64
|
+
Returns
|
|
65
|
+
-------
|
|
66
|
+
ndarray of shape (N + 1,)
|
|
67
|
+
Coefficients ``g_k``, ordered by increasing power of ``z`` (i.e.
|
|
68
|
+
``g[k]`` is the coefficient of ``z**k``).
|
|
69
|
+
"""
|
|
70
|
+
configs = np.arange(2**N, dtype=np.int64)
|
|
71
|
+
bits = (configs[:, None] >> np.arange(N)) & 1
|
|
72
|
+
spins = bits.astype(np.float64) * 2 - 1 # shape (2**N, N), values +/-1
|
|
73
|
+
|
|
74
|
+
if periodic:
|
|
75
|
+
neighbor_product = spins * np.roll(spins, -1, axis=1)
|
|
76
|
+
else:
|
|
77
|
+
neighbor_product = spins[:, :-1] * spins[:, 1:]
|
|
78
|
+
E0 = -J * np.sum(neighbor_product, axis=1)
|
|
79
|
+
|
|
80
|
+
n_up = np.sum(bits, axis=1)
|
|
81
|
+
weights = np.exp(-beta * E0)
|
|
82
|
+
|
|
83
|
+
g = np.zeros(N + 1, dtype=np.float64)
|
|
84
|
+
np.add.at(g, n_up, weights)
|
|
85
|
+
return g
|
|
86
|
+
|
|
87
|
+
|
|
88
|
+
def yang_lee_zeros(coeffs):
|
|
89
|
+
"""Roots, in the complex fugacity plane, of the polynomial :math:`\\sum_k g_k z^k`.
|
|
90
|
+
|
|
91
|
+
Lee and Yang's circle theorem predicts that for a ferromagnetic Ising
|
|
92
|
+
system (``J > 0`` in :func:`ising_partition_polynomial`), every one of
|
|
93
|
+
these roots lies exactly on the unit circle :math:`|z| = 1`, regardless
|
|
94
|
+
of system size -- a striking, exact constraint on where a phase
|
|
95
|
+
transition's mathematical signature is allowed to live.
|
|
96
|
+
|
|
97
|
+
Parameters
|
|
98
|
+
----------
|
|
99
|
+
coeffs : array_like
|
|
100
|
+
Polynomial coefficients ``g_k``, ordered by increasing power of
|
|
101
|
+
``z`` (as returned by :func:`ising_partition_polynomial`).
|
|
102
|
+
|
|
103
|
+
Returns
|
|
104
|
+
-------
|
|
105
|
+
ndarray of complex
|
|
106
|
+
The polynomial's roots.
|
|
107
|
+
"""
|
|
108
|
+
coeffs = np.asarray(coeffs, dtype=np.float64)
|
|
109
|
+
return np.roots(coeffs[::-1])
|
|
@@ -0,0 +1,356 @@
|
|
|
1
|
+
"""Thermodynamic observables derived from Monte Carlo and molecular dynamics samples.
|
|
2
|
+
|
|
3
|
+
Every function here takes arrays of samples collected during a simulation
|
|
4
|
+
(energies, magnetizations, velocities, spin configurations, ...) and returns a
|
|
5
|
+
scalar or array observable, following the standard fluctuation-dissipation
|
|
6
|
+
relations of the canonical ensemble.
|
|
7
|
+
"""
|
|
8
|
+
|
|
9
|
+
from __future__ import annotations
|
|
10
|
+
|
|
11
|
+
import numpy as np
|
|
12
|
+
|
|
13
|
+
__all__ = [
|
|
14
|
+
"bec_condensate_fraction",
|
|
15
|
+
"binder_cumulant",
|
|
16
|
+
"bose_einstein_occupation",
|
|
17
|
+
"fermi_dirac_occupation",
|
|
18
|
+
"maxwell_boltzmann_component_pdf",
|
|
19
|
+
"maxwell_boltzmann_speed_pdf",
|
|
20
|
+
"specific_heat",
|
|
21
|
+
"spin_correlation_function",
|
|
22
|
+
"susceptibility",
|
|
23
|
+
]
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
def specific_heat(energies, temperature, n_sites, kB=1.0):
|
|
27
|
+
"""Specific heat per site from the energy fluctuations of a canonical sample.
|
|
28
|
+
|
|
29
|
+
.. math::
|
|
30
|
+
|
|
31
|
+
C_v = \\frac{\\langle E^2 \\rangle - \\langle E \\rangle^2}{k_B T^2 N}
|
|
32
|
+
|
|
33
|
+
Parameters
|
|
34
|
+
----------
|
|
35
|
+
energies : array_like
|
|
36
|
+
Sampled total energies at fixed temperature.
|
|
37
|
+
temperature : float
|
|
38
|
+
Sampling temperature.
|
|
39
|
+
n_sites : int
|
|
40
|
+
Number of lattice sites (or particles) ``N``, used to report an
|
|
41
|
+
intensive, per-site quantity.
|
|
42
|
+
kB : float, default=1.0
|
|
43
|
+
Boltzmann constant.
|
|
44
|
+
|
|
45
|
+
Returns
|
|
46
|
+
-------
|
|
47
|
+
float
|
|
48
|
+
Specific heat per site.
|
|
49
|
+
|
|
50
|
+
Examples
|
|
51
|
+
--------
|
|
52
|
+
>>> rng = np.random.default_rng(0)
|
|
53
|
+
>>> E = rng.normal(loc=-100.0, scale=5.0, size=10000)
|
|
54
|
+
>>> bool(specific_heat(E, temperature=2.0, n_sites=64) > 0)
|
|
55
|
+
True
|
|
56
|
+
"""
|
|
57
|
+
energies = np.asarray(energies, dtype=np.float64)
|
|
58
|
+
var_E = energies.var()
|
|
59
|
+
return var_E / (kB * temperature**2 * n_sites)
|
|
60
|
+
|
|
61
|
+
|
|
62
|
+
def susceptibility(magnetizations, temperature, n_sites, kB=1.0):
|
|
63
|
+
"""Magnetic susceptibility per site from magnetization fluctuations.
|
|
64
|
+
|
|
65
|
+
.. math::
|
|
66
|
+
|
|
67
|
+
\\chi = \\frac{\\langle M^2 \\rangle - \\langle M \\rangle^2}{k_B T N}
|
|
68
|
+
|
|
69
|
+
Parameters
|
|
70
|
+
----------
|
|
71
|
+
magnetizations : array_like
|
|
72
|
+
Sampled total magnetizations at fixed temperature.
|
|
73
|
+
temperature : float
|
|
74
|
+
Sampling temperature.
|
|
75
|
+
n_sites : int
|
|
76
|
+
Number of lattice sites ``N``.
|
|
77
|
+
kB : float, default=1.0
|
|
78
|
+
Boltzmann constant.
|
|
79
|
+
|
|
80
|
+
Returns
|
|
81
|
+
-------
|
|
82
|
+
float
|
|
83
|
+
Susceptibility per site.
|
|
84
|
+
"""
|
|
85
|
+
magnetizations = np.asarray(magnetizations, dtype=np.float64)
|
|
86
|
+
var_M = magnetizations.var()
|
|
87
|
+
return var_M / (kB * temperature * n_sites)
|
|
88
|
+
|
|
89
|
+
|
|
90
|
+
def binder_cumulant(magnetizations):
|
|
91
|
+
"""Fourth-order Binder cumulant of a magnetization sample.
|
|
92
|
+
|
|
93
|
+
.. math::
|
|
94
|
+
|
|
95
|
+
U_4 = 1 - \\frac{\\langle M^4 \\rangle}{3 \\langle M^2 \\rangle^2}
|
|
96
|
+
|
|
97
|
+
``U_4`` is a standard finite-size-scaling diagnostic: it is
|
|
98
|
+
size-independent exactly at the critical temperature, which makes
|
|
99
|
+
crossing plots for several lattice sizes a robust way to locate
|
|
100
|
+
:math:`T_c`.
|
|
101
|
+
|
|
102
|
+
Parameters
|
|
103
|
+
----------
|
|
104
|
+
magnetizations : array_like
|
|
105
|
+
Sampled total (or per-site) magnetizations.
|
|
106
|
+
|
|
107
|
+
Returns
|
|
108
|
+
-------
|
|
109
|
+
float
|
|
110
|
+
The Binder cumulant, in :math:`[0, 2/3]` for a symmetric
|
|
111
|
+
distribution.
|
|
112
|
+
"""
|
|
113
|
+
m = np.asarray(magnetizations, dtype=np.float64)
|
|
114
|
+
m2 = np.mean(m**2)
|
|
115
|
+
m4 = np.mean(m**4)
|
|
116
|
+
return 1.0 - m4 / (3.0 * m2**2)
|
|
117
|
+
|
|
118
|
+
|
|
119
|
+
def spin_correlation_function(spins, max_r=None):
|
|
120
|
+
"""Radially averaged equal-time spin-spin correlation function :math:`G(r)`.
|
|
121
|
+
|
|
122
|
+
Computed efficiently via the Wiener-Khinchin theorem: the autocorrelation
|
|
123
|
+
of a periodic field equals the inverse FFT of its power spectrum.
|
|
124
|
+
|
|
125
|
+
.. math::
|
|
126
|
+
|
|
127
|
+
G(r) = \\langle s_0 s_r \\rangle - \\langle s \\rangle^2
|
|
128
|
+
|
|
129
|
+
averaged over all site pairs at (periodic, Euclidean-rounded) separation
|
|
130
|
+
``r``.
|
|
131
|
+
|
|
132
|
+
Parameters
|
|
133
|
+
----------
|
|
134
|
+
spins : ndarray of shape (L, L)
|
|
135
|
+
Spin (or angle-cosine) configuration on a periodic square lattice.
|
|
136
|
+
max_r : int, optional
|
|
137
|
+
Largest separation to report. Defaults to ``L // 2``.
|
|
138
|
+
|
|
139
|
+
Returns
|
|
140
|
+
-------
|
|
141
|
+
r : ndarray of shape (max_r,)
|
|
142
|
+
Integer separations ``0, 1, ..., max_r - 1``.
|
|
143
|
+
G : ndarray of shape (max_r,)
|
|
144
|
+
Correlation function averaged over all pairs at each rounded
|
|
145
|
+
separation.
|
|
146
|
+
"""
|
|
147
|
+
spins = np.asarray(spins, dtype=np.float64)
|
|
148
|
+
L = spins.shape[0]
|
|
149
|
+
if max_r is None:
|
|
150
|
+
max_r = L // 2
|
|
151
|
+
|
|
152
|
+
mean_s = spins.mean()
|
|
153
|
+
fft = np.fft.fft2(spins)
|
|
154
|
+
autocorr = np.fft.ifft2(fft * np.conj(fft)).real / (L * L)
|
|
155
|
+
|
|
156
|
+
ii, jj = np.meshgrid(np.arange(L), np.arange(L), indexing="ij")
|
|
157
|
+
di = np.minimum(ii, L - ii)
|
|
158
|
+
dj = np.minimum(jj, L - jj)
|
|
159
|
+
dist = np.sqrt(di**2 + dj**2)
|
|
160
|
+
r_bin = np.round(dist).astype(int)
|
|
161
|
+
|
|
162
|
+
G = np.zeros(max_r, dtype=np.float64)
|
|
163
|
+
for r in range(max_r):
|
|
164
|
+
mask = r_bin == r
|
|
165
|
+
if np.any(mask):
|
|
166
|
+
G[r] = autocorr[mask].mean() - mean_s**2
|
|
167
|
+
return np.arange(max_r), G
|
|
168
|
+
|
|
169
|
+
|
|
170
|
+
def maxwell_boltzmann_speed_pdf(v, temperature, mass=1.0, kB=1.0, dim=2):
|
|
171
|
+
"""Equilibrium Maxwell-Boltzmann probability density of the speed :math:`|v|`.
|
|
172
|
+
|
|
173
|
+
In :math:`d` dimensions,
|
|
174
|
+
|
|
175
|
+
.. math::
|
|
176
|
+
|
|
177
|
+
f(v) = v^{d-1}
|
|
178
|
+
\\left(\\frac{m}{2\\pi k_B T}\\right)^{d/2}
|
|
179
|
+
S_{d-1} \\, e^{-m v^2 / 2 k_B T}
|
|
180
|
+
|
|
181
|
+
where :math:`S_{d-1}` is the surface area of the unit :math:`(d-1)`-sphere
|
|
182
|
+
(:math:`2` for :math:`d=1`, :math:`2\\pi` for :math:`d=2`, :math:`4\\pi`
|
|
183
|
+
for :math:`d=3`).
|
|
184
|
+
|
|
185
|
+
Parameters
|
|
186
|
+
----------
|
|
187
|
+
v : array_like
|
|
188
|
+
Speed values (must be non-negative) at which to evaluate the density.
|
|
189
|
+
temperature : float
|
|
190
|
+
Temperature.
|
|
191
|
+
mass : float, default=1.0
|
|
192
|
+
Particle mass.
|
|
193
|
+
kB : float, default=1.0
|
|
194
|
+
Boltzmann constant.
|
|
195
|
+
dim : {1, 2, 3}, default=2
|
|
196
|
+
Spatial dimension.
|
|
197
|
+
|
|
198
|
+
Returns
|
|
199
|
+
-------
|
|
200
|
+
ndarray
|
|
201
|
+
Probability density :math:`f(v)`, normalized so that
|
|
202
|
+
:math:`\\int_0^\\infty f(v)\\, dv = 1`.
|
|
203
|
+
"""
|
|
204
|
+
v = np.asarray(v, dtype=np.float64)
|
|
205
|
+
beta_m = mass / (kB * temperature)
|
|
206
|
+
if dim == 1:
|
|
207
|
+
surface = 2.0
|
|
208
|
+
elif dim == 2:
|
|
209
|
+
surface = 2.0 * np.pi
|
|
210
|
+
elif dim == 3:
|
|
211
|
+
surface = 4.0 * np.pi
|
|
212
|
+
else:
|
|
213
|
+
raise ValueError("dim must be 1, 2, or 3")
|
|
214
|
+
prefactor = surface * (beta_m / (2.0 * np.pi)) ** (dim / 2.0)
|
|
215
|
+
return prefactor * v ** (dim - 1) * np.exp(-0.5 * beta_m * v**2)
|
|
216
|
+
|
|
217
|
+
|
|
218
|
+
def maxwell_boltzmann_component_pdf(vx, temperature, mass=1.0, kB=1.0):
|
|
219
|
+
"""Equilibrium Gaussian density of a single Cartesian velocity component.
|
|
220
|
+
|
|
221
|
+
.. math::
|
|
222
|
+
|
|
223
|
+
f(v_x) = \\sqrt{\\frac{m}{2\\pi k_B T}} \\, e^{-m v_x^2 / 2 k_B T}
|
|
224
|
+
|
|
225
|
+
Parameters
|
|
226
|
+
----------
|
|
227
|
+
vx : array_like
|
|
228
|
+
Velocity component values.
|
|
229
|
+
temperature : float
|
|
230
|
+
Temperature.
|
|
231
|
+
mass : float, default=1.0
|
|
232
|
+
Particle mass.
|
|
233
|
+
kB : float, default=1.0
|
|
234
|
+
Boltzmann constant.
|
|
235
|
+
|
|
236
|
+
Returns
|
|
237
|
+
-------
|
|
238
|
+
ndarray
|
|
239
|
+
Probability density :math:`f(v_x)`.
|
|
240
|
+
"""
|
|
241
|
+
vx = np.asarray(vx, dtype=np.float64)
|
|
242
|
+
beta_m = mass / (kB * temperature)
|
|
243
|
+
return np.sqrt(beta_m / (2.0 * np.pi)) * np.exp(-0.5 * beta_m * vx**2)
|
|
244
|
+
|
|
245
|
+
|
|
246
|
+
def bose_einstein_occupation(energy, mu, temperature, kB=1.0):
|
|
247
|
+
"""Mean occupation number of a bosonic single-particle state, the Bose-Einstein distribution.
|
|
248
|
+
|
|
249
|
+
.. math::
|
|
250
|
+
|
|
251
|
+
n_{\\text{BE}}(\\varepsilon) = \\frac{1}{e^{(\\varepsilon - \\mu)/k_B T} - 1}
|
|
252
|
+
|
|
253
|
+
Unlike Fermi-Dirac statistics, there is no restriction on how many
|
|
254
|
+
identical bosons can occupy the same state; as the chemical potential
|
|
255
|
+
:math:`\\mu` approaches the ground-state energy from below, the
|
|
256
|
+
ground-state occupation diverges -- the onset of Bose-Einstein
|
|
257
|
+
condensation.
|
|
258
|
+
|
|
259
|
+
Parameters
|
|
260
|
+
----------
|
|
261
|
+
energy : array_like
|
|
262
|
+
Single-particle state energies. Must satisfy ``energy > mu``
|
|
263
|
+
(otherwise the occupation is unphysical).
|
|
264
|
+
mu : float
|
|
265
|
+
Chemical potential.
|
|
266
|
+
temperature : float
|
|
267
|
+
Temperature.
|
|
268
|
+
kB : float, default=1.0
|
|
269
|
+
Boltzmann constant.
|
|
270
|
+
|
|
271
|
+
Returns
|
|
272
|
+
-------
|
|
273
|
+
ndarray
|
|
274
|
+
Mean occupation number :math:`n_{\\text{BE}}(\\varepsilon)`.
|
|
275
|
+
"""
|
|
276
|
+
x = (np.asarray(energy, dtype=np.float64) - mu) / (kB * temperature)
|
|
277
|
+
return 1.0 / np.expm1(x)
|
|
278
|
+
|
|
279
|
+
|
|
280
|
+
def fermi_dirac_occupation(energy, mu, temperature, kB=1.0):
|
|
281
|
+
"""Mean occupation number of a fermionic single-particle state, the Fermi-Dirac distribution.
|
|
282
|
+
|
|
283
|
+
.. math::
|
|
284
|
+
|
|
285
|
+
n_{\\text{FD}}(\\varepsilon) = \\frac{1}{e^{(\\varepsilon - \\mu)/k_B T} + 1}
|
|
286
|
+
|
|
287
|
+
The Pauli exclusion principle caps :math:`n_{\\text{FD}}` at 1 for every
|
|
288
|
+
state, in sharp contrast to Bose-Einstein statistics; as :math:`T \\to
|
|
289
|
+
0`, this sharpens into a step function at the Fermi energy
|
|
290
|
+
:math:`\\varepsilon = \\mu`.
|
|
291
|
+
|
|
292
|
+
Parameters
|
|
293
|
+
----------
|
|
294
|
+
energy : array_like
|
|
295
|
+
Single-particle state energies.
|
|
296
|
+
mu : float
|
|
297
|
+
Chemical potential (the Fermi energy at :math:`T = 0`).
|
|
298
|
+
temperature : float
|
|
299
|
+
Temperature.
|
|
300
|
+
kB : float, default=1.0
|
|
301
|
+
Boltzmann constant.
|
|
302
|
+
|
|
303
|
+
Returns
|
|
304
|
+
-------
|
|
305
|
+
ndarray
|
|
306
|
+
Mean occupation number :math:`n_{\\text{FD}}(\\varepsilon) \\in (0, 1)`.
|
|
307
|
+
|
|
308
|
+
Examples
|
|
309
|
+
--------
|
|
310
|
+
>>> import numpy as np
|
|
311
|
+
>>> bool(np.all(fermi_dirac_occupation(np.array([0.0, 1.0, 2.0]), mu=1.0, temperature=0.01) >= 0))
|
|
312
|
+
True
|
|
313
|
+
"""
|
|
314
|
+
x = (np.asarray(energy, dtype=np.float64) - mu) / (kB * temperature)
|
|
315
|
+
with np.errstate(over="ignore"):
|
|
316
|
+
# exp(x) legitimately overflows to inf deep in the low-T step-function
|
|
317
|
+
# limit; 1/(inf+1) still gives the mathematically correct 0 occupation.
|
|
318
|
+
return 1.0 / (np.exp(x) + 1.0)
|
|
319
|
+
|
|
320
|
+
|
|
321
|
+
def bec_condensate_fraction(temperature, critical_temperature):
|
|
322
|
+
"""Condensate fraction of an ideal, homogeneous 3D Bose gas below the BEC transition.
|
|
323
|
+
|
|
324
|
+
.. math::
|
|
325
|
+
|
|
326
|
+
\\frac{N_0}{N} =
|
|
327
|
+
\\begin{cases}
|
|
328
|
+
1 - (T / T_c)^{3/2} & T < T_c \\\\
|
|
329
|
+
0 & T \\ge T_c
|
|
330
|
+
\\end{cases}
|
|
331
|
+
|
|
332
|
+
A textbook prediction of Bose-Einstein statistics for a trapped ideal
|
|
333
|
+
gas, first confirmed experimentally in 1995 in dilute alkali-atom gases
|
|
334
|
+
(Cornell and Wieman; Ketterle; 2001 Nobel Prize in Physics).
|
|
335
|
+
|
|
336
|
+
Parameters
|
|
337
|
+
----------
|
|
338
|
+
temperature : array_like
|
|
339
|
+
Temperature(s) at which to evaluate the condensate fraction.
|
|
340
|
+
critical_temperature : float
|
|
341
|
+
The BEC transition temperature :math:`T_c`.
|
|
342
|
+
|
|
343
|
+
Returns
|
|
344
|
+
-------
|
|
345
|
+
ndarray
|
|
346
|
+
Condensate fraction :math:`N_0/N \\in [0, 1]`.
|
|
347
|
+
|
|
348
|
+
Examples
|
|
349
|
+
--------
|
|
350
|
+
>>> f = bec_condensate_fraction(np.array([0.0, 0.5, 1.0, 2.0]), critical_temperature=1.0)
|
|
351
|
+
>>> [round(float(v), 3) for v in f]
|
|
352
|
+
[1.0, 0.646, 0.0, 0.0]
|
|
353
|
+
"""
|
|
354
|
+
T = np.asarray(temperature, dtype=np.float64)
|
|
355
|
+
fraction = 1.0 - (T / critical_temperature) ** 1.5
|
|
356
|
+
return np.where(critical_temperature > T, fraction, 0.0)
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
"""Matplotlib- and Plotly-based visualizers for every physicskit.statphys chapter.
|
|
2
|
+
|
|
3
|
+
- :mod:`physicskit.statphys.visualizers.lattice_render` -- spin grid heatmaps, sweep
|
|
4
|
+
animations, thermodynamic diagnostic plots, and percolation cluster and
|
|
5
|
+
cluster-size-distribution plots.
|
|
6
|
+
- :mod:`physicskit.statphys.visualizers.vortex_render` -- XY model vector fields and
|
|
7
|
+
topological vortex/antivortex overlays.
|
|
8
|
+
- :mod:`physicskit.statphys.visualizers.particle_render` -- Lennard-Jones gas snapshots,
|
|
9
|
+
velocity histograms, and motion animations.
|
|
10
|
+
- :mod:`physicskit.statphys.visualizers.rg_render` -- side-by-side block-spin
|
|
11
|
+
renormalization group flow panels.
|
|
12
|
+
- :mod:`physicskit.statphys.visualizers.random_walk_render` -- walk trajectories, MSD,
|
|
13
|
+
and central-limit-theorem histograms.
|
|
14
|
+
- :mod:`physicskit.statphys.visualizers.sandpile_render` -- sandpile heights and
|
|
15
|
+
avalanche size distributions.
|
|
16
|
+
- :mod:`physicskit.statphys.visualizers.urn_render` -- Ehrenfest urn relaxation and
|
|
17
|
+
entropy history.
|
|
18
|
+
- :mod:`physicskit.statphys.visualizers.spin_glass_render` -- spin-glass replica-overlap
|
|
19
|
+
distributions.
|
|
20
|
+
- :mod:`physicskit.statphys.visualizers.kpz_render` -- RSOS interface profiles and
|
|
21
|
+
width-growth scaling.
|
|
22
|
+
- :mod:`physicskit.statphys.visualizers.jarzynski_render` -- nonequilibrium work
|
|
23
|
+
distributions and free-energy estimates.
|
|
24
|
+
- :mod:`physicskit.statphys.visualizers.interactive` -- Plotly-based interactive
|
|
25
|
+
counterparts of the temperature sweep, vortex field, and particle
|
|
26
|
+
snapshot plots.
|
|
27
|
+
"""
|
|
28
|
+
|
|
29
|
+
from physicskit.statphys.visualizers.interactive import (
|
|
30
|
+
interactive_particle_snapshot,
|
|
31
|
+
interactive_temperature_sweep,
|
|
32
|
+
interactive_vortex_field,
|
|
33
|
+
)
|
|
34
|
+
from physicskit.statphys.visualizers.jarzynski_render import plot_work_distribution
|
|
35
|
+
from physicskit.statphys.visualizers.kpz_render import plot_interface_profile, plot_width_growth
|
|
36
|
+
from physicskit.statphys.visualizers.lattice_render import (
|
|
37
|
+
animate_lattice_sweeps,
|
|
38
|
+
plot_cluster_size_distribution,
|
|
39
|
+
plot_percolation_clusters,
|
|
40
|
+
plot_spin_grid,
|
|
41
|
+
plot_thermodynamics,
|
|
42
|
+
)
|
|
43
|
+
from physicskit.statphys.visualizers.particle_render import (
|
|
44
|
+
animate_gas,
|
|
45
|
+
plot_particle_snapshot,
|
|
46
|
+
plot_velocity_histogram,
|
|
47
|
+
)
|
|
48
|
+
from physicskit.statphys.visualizers.random_walk_render import (
|
|
49
|
+
plot_clt_histogram,
|
|
50
|
+
plot_msd,
|
|
51
|
+
plot_trajectories_2d,
|
|
52
|
+
)
|
|
53
|
+
from physicskit.statphys.visualizers.rg_render import plot_rg_flow
|
|
54
|
+
from physicskit.statphys.visualizers.sandpile_render import (
|
|
55
|
+
plot_avalanche_size_distribution,
|
|
56
|
+
plot_sandpile_heights,
|
|
57
|
+
)
|
|
58
|
+
from physicskit.statphys.visualizers.spin_glass_render import plot_overlap_distribution
|
|
59
|
+
from physicskit.statphys.visualizers.urn_render import plot_ehrenfest_history
|
|
60
|
+
from physicskit.statphys.visualizers.vortex_render import plot_vortices, plot_xy_vector_field
|
|
61
|
+
|
|
62
|
+
__all__ = [
|
|
63
|
+
"animate_gas",
|
|
64
|
+
"animate_lattice_sweeps",
|
|
65
|
+
"interactive_particle_snapshot",
|
|
66
|
+
"interactive_temperature_sweep",
|
|
67
|
+
"interactive_vortex_field",
|
|
68
|
+
"plot_avalanche_size_distribution",
|
|
69
|
+
"plot_clt_histogram",
|
|
70
|
+
"plot_cluster_size_distribution",
|
|
71
|
+
"plot_ehrenfest_history",
|
|
72
|
+
"plot_interface_profile",
|
|
73
|
+
"plot_msd",
|
|
74
|
+
"plot_overlap_distribution",
|
|
75
|
+
"plot_particle_snapshot",
|
|
76
|
+
"plot_percolation_clusters",
|
|
77
|
+
"plot_rg_flow",
|
|
78
|
+
"plot_sandpile_heights",
|
|
79
|
+
"plot_spin_grid",
|
|
80
|
+
"plot_thermodynamics",
|
|
81
|
+
"plot_trajectories_2d",
|
|
82
|
+
"plot_velocity_histogram",
|
|
83
|
+
"plot_vortices",
|
|
84
|
+
"plot_width_growth",
|
|
85
|
+
"plot_work_distribution",
|
|
86
|
+
"plot_xy_vector_field",
|
|
87
|
+
]
|