Damping#

(added in version 0.3.0)

Built in damper module implementations

Description#

Damping is used to numerically stabilize the simulations.

Available Damping

DamperBase

Base class for damping module implementations.

AnalyticalLinearDamper

Analytical linear damper class.

LaplaceDissipationFilter

Laplace Dissipation Filter class.

Compatibility#

Damping/Numerical Dissipation

Rod

Rigid Body

AnalyticalLinearDamper

LaplaceDissipationFilter

Built-in Dampers#

class elastica.dissipation.DamperBase(*args, **kwargs)[source]#

Bases: Generic[T], ABC

Base class for damping module implementations.

Attributes:
systemRodBase

get system (rod or rigid body) reference

Notes

All damper classes must inherit DamperBase class.

property system: T#

get system (rod or rigid body) reference

Returns:
SystemType
abstract dampen_rates(system, time)[source]#

Dampen rates (velocity and/or omega) of a rod object.

Return type:

None

Parameters:
systemSystemType

System (rod or rigid-body) object.

timefloat

The time of simulation.

class elastica.dissipation.AnalyticalLinearDamper(time_step, **kwargs)[source]#

Analytical linear damper class. This class corresponds to the analytical version of a linear damper, and uses the following equations to damp translational and rotational velocities:

\[ \begin{align}\begin{aligned}m \frac{\partial \mathbf{v}}{\partial t} = -\gamma_t \mathbf{v}\\\frac{\mathbf{J}}{e} \frac{\partial \pmb{\omega}}{\partial t} = -\gamma_r \pmb{\omega}\end{aligned}\end{align} \]

Notes

Since this class analytically treats the damping term, it is unconditionally stable from a timestep perspective, i.e. the presence of damping does not impose any additional restriction on the simulation timestep size. This implies that when using AnalyticalLinearDamper, one can set damping_constant as high as possible, without worrying about the simulation becoming unstable. This now leads to a streamlined procedure for tuning the damping_constant:

  1. Set a high value for damping_constant to first achieve a stable simulation.

  2. If you feel the simulation is overdamped, reduce damping_constant until you feel the simulation is underdamped, and expected dynamics are recovered.

Examples

The current AnalyticalLinearDamper class supports three types of protocols:

  1. Uniform damping constant: the user provides the keyword argument uniform_damping_constant of dimension (1/T). This leads to an exponential damping constant that is used for both translation and rotational velocities.

>>> simulator.dampen(rod).using(
...     AnalyticalLinearDamper,
...     uniform_damping_constant=0.1,
...     time_step = 1E-4,   # Simulation time-step
... )
  1. Physical damping constant: separate exponential coefficients are computed for the translational and rotational velocities, based on user-defined translational_damping_constant and rotational_damping_constant.

>>> simulator.dampen(rod).using(
...     AnalyticalLinearDamper,
...     translational_damping_constant=0.1,
...     rotational_damping_constant=0.05,
...     time_step = 1E-4,   # Simulation time-step
... )
  1. Damping constant: this protocol follows the original algorithm where the damping constants for translational and rotational velocities are assumed to be numerically identical. This leads to dimensional inconsistencies (see GazzolaLab/PyElastica#354).

>>> simulator.dampen(rod).using(
...     AnalyticalLinearDamper,
...     damping_constant=0.1,
...     time_step=1E-4,
... )
__init__(time_step, **kwargs)[source]#

Initialize damping module

Parameters:
*argsAny

Positional arguments (not currently used, reserved for future use).

**kwargsAny

Keyword arguments. Must include ‘_system’ key containing the system (rod or rigid body) to be damped. Additional keyword arguments are passed to derived classes for their specific configuration.

Raises:
KeyError

If ‘_system’ is not provided in kwargs. This typically indicates incorrect usage - use simulator.dampen(…).using(…) syntax instead.

Notes

The base class extracts the ‘_system’ parameter from kwargs. Derived damper classes (e.g., AnalyticalLinearDamper, LaplaceDissipationFilter) may accept additional keyword arguments for their specific configuration.

class elastica.dissipation.LaplaceDissipationFilter(filter_order, **kwargs)[source]#

Laplace Dissipation Filter class. This class corresponds qualitatively to a low-pass filter generated via the 1D Laplacian operator. It is applied to the translational and rotational velocities, where it filters out the high frequency (noise) modes, while having negligible effect on the low frequency smooth modes.

Attributes:
filter_orderint

Filter order, which corresponds to the number of times the Laplacian operator is applied. Increasing filter_order implies higher-order/weaker filtering.

velocity_filter_term: numpy.ndarray

2D array containing data with ‘float’ type. Filter term that modifies rod translational velocity.

omega_filter_term: numpy.ndarray

2D array containing data with ‘float’ type. Filter term that modifies rod rotational velocity.

Notes

The extent of filtering can be controlled by the filter_order, which refers to the number of times the Laplacian operator is applied. Small integer values (1, 2, etc.) result in aggressive filtering, and can lead to the “physics” being filtered out. While high values (9, 10, etc.) imply minimal filtering, and thus negligible effect on the velocities. Values in the range of 3-7 are usually recommended.

For details regarding the numerics behind the filtering, refer to [1], [2].

[1]

Jeanmart, H., & Winckelmans, G. (2007). Investigation of eddy-viscosity models modified using discrete filters: a simplified “regularized variational multiscale model” and an “enhanced field model”. Physics of fluids, 19(5), 055110.

[2]

Lorieul, G. (2018). Development and validation of a 2D Vortex Particle-Mesh method for incompressible multiphase flows (Doctoral dissertation, Université Catholique de Louvain).

Examples

How to set Laplace dissipation filter for rod:

>>> simulator.dampen(rod).using(
...     LaplaceDissipationFilter,
...     filter_order=3,   # order of the filter
... )
__init__(filter_order, **kwargs)[source]#

Filter damper initializer.

Parameters:
filter_orderint

Filter order, which corresponds to the number of times the Laplacian operator is applied. Increasing filter_order implies higher-order/weaker filtering.

Raises:
ValueError

If filter_order is not a positive integer.