Traits used for potentials¶
As mentioned above, potential functions can be used to model all kinds of
interactions between particles such as bonded and non-bonded interactions. In
Lumol, Potential
is a trait. To further distinguish between
bonded interactions (bond lengths, angles and dihedrals) and non-bonded
interactions, we use another trait (often called marker traits). Your possible
options to further specialise a Potential
are
- PairPotential for non-bonded two body interactions;
- BondPotential for covalent bonds interactions;
- AnglePotential for covalent angles interactions;
- DihedralPotential for covalent dihedral angles interactions.
For our Mie potential implementation, we will have to implement both the
Potential
as well as the PairPotential
traits. If we wanted to implement
a function that can be used as non-bonded as well as bond-length potential, we’d
have to implement Potential
, PairPotential
as well as BondPotential
.
“Implementing a trait” means that we will define a struct for which we will
add functions to satisfy the traits’ requirements.
Let’s start by having a look at the documentation for Potential
: open the
API documentation. As you can see from the trait, a
Potential
defines two functions, energy
and force
(we ignore the
Sync + Send
statement for now):
pub trait Potential: Sync + Send {
fn energy(&self, x: f64) -> f64;
fn force(&self, x: f64) -> f64;
}
energy
will compute the interaction energy between atoms as a function of
x
. The force is defined as the negative derivative of the energy function
with respect to x
.
Both functions take a single, scalar argument and return a single scalar value.
In our case x
stands for the distance between two interaction sites. Note
that only the function definitions – without a function body – are specified.
We will have to implement these functions for our potential.