Source code for struphy.models.vlasov

import copy

from feectools.ddm.mpi import mpi as MPI

from struphy import BaseUnits
from struphy.io.options import LiteralOptions
from struphy.models.base import StruphyModel
from struphy.models.scalars import KineticEnergyPIC, Scalars
from struphy.models.species import (
    ParticleSpecies,
)
from struphy.models.variables import PICVariable
from struphy.propagators.push_eta import PushEta
from struphy.propagators.push_vxb import PushVxB

rank = MPI.COMM_WORLD.Get_rank()


[docs] class Vlasov(StruphyModel): """Vlasov equation for a single species in a static background magnetic field. Parameters ---------- base_units: BaseUnits Base units for normalization (default: BaseUnits()) charge_number: int Charge number (in units of the positive elementary charge) of the species (default: 1) mass_number: float Mass number (in units of Proton mass) of the species (default: 1.0) """ @classmethod def model_type(cls) -> LiteralOptions.ModelTypes: return "Kinetic" ## species class KineticIons(ParticleSpecies): def __init__( self, charge_number: int = 1, mass_number: float = 1.0, ): self.var = PICVariable(space="Particles6D") self.init_variables( charge_number=charge_number, mass_number=mass_number, ) ## propagators class Propagators: def __init__(self): self.push_vxb = PushVxB() self.push_eta = PushEta() ## abstract methods def __init__( self, base_units: BaseUnits = BaseUnits(), charge_number: int = 1, mass_number: float = 1.0, ): # 0. store input parameters self.params = copy.deepcopy(locals()) # 1. instantiate all species self.kinetic_ions = self.KineticIons( charge_number, mass_number, ) # 2. derive units (must be done after instantiating species to access charge and mass numbers) self.setup_equation_params(base_units=base_units) # 3. instantiate all propagators self.propagators = self.Propagators() # 4. assign variables to propagators self.propagators.push_vxb.variables.ions = self.kinetic_ions.var self.propagators.push_eta.variables.var = self.kinetic_ions.var # 5. define scalars to be tracked during simulation kinetic_energy = KineticEnergyPIC(self.kinetic_ions.var) self.scalars = Scalars(kinetic_energy=kinetic_energy) @property def bulk_species(self): return self.kinetic_ions @property def velocity_scale(self): return "cyclotron" def allocate_helpers(self): pass
[docs] @classmethod def doc_pde(cls): r"""**PDEs solved by model:** Vlasov equation: .. math:: \frac{\partial f}{\partial t} + \mathbf{v} \cdot \nabla f + \left( \mathbf{v} \times \mathbf{B}_0 \right) \cdot \frac{\partial f}{\partial \mathbf{v}} = 0 """
[docs] @classmethod def doc_normalization(cls): r"""The characteristic speed is the cyclotron scale .. math:: \hat v = \hat\Omega_c \hat x. """
[docs] @classmethod def doc_scalar_quantities(cls): r"""**The following scalars are tracked during simulation:** - Particle kinetic energy: ``kinetic_energy``"""
[docs] @classmethod def doc_discretization(cls): """Time integration is performed by the following propagators (in sequence): 1. :class:`~struphy.propagators.push_vxb.PushVxB` 2. :class:`~struphy.propagators.push_eta.PushEta` """ doc = rf"""**1. push_vxb.PushVxB:** {PushVxB.__doc__} **2. push_eta.PushEta:** {PushEta.__doc__} """ return doc
[docs] @classmethod def doc_long_description(cls): r"""Vlasov is the simplest kinetic test-particle model in the 6D hierarchy. It evolves particles in a static magnetic background without electric or magnetic self-consistency."""
[docs] @classmethod def doc_examples(cls): r"""Create and initialize a Vlasov test-particle model: .. code-block:: python from struphy.models import Vlasov model = Vlasov() model.kinetic_ions.var """
[docs] @classmethod def doc_use_cases(cls): r"""This model is appropriate for: - test-particle motion in prescribed magnetic fields - verification of the Boris-like VxB and PushEta splitting - reduced kinetic transport studies without field feedback"""
[docs] @classmethod def doc_cannot_be_used_for(cls): r"""This model is not suitable for: - self-consistent electrostatic or electromagnetic coupling - collisional kinetic dynamics - guiding-center reduction studies - fluid or MHD-scale closures"""