Interacting Particles

In this section we are going to take a shot at the problem of interacting particles. A typical application of this problem is to the motion of charged plasma particles that interact electrostatically with each other. Plasmas are actually even more complex, because accelerated particles radiate and some of this radiation may be captured by other particles, and this adds enormous complexity to the models. Other applications include molecular dynamics and, right at the other end of the spectrum, galactic dynamics.

As far as MPI is concerned, we are going to take another look at defining MPI types and at collective communications. We are going to arrange all particles into an array and the way that this array is going to be partitioned between processes of the computational pool is very reminiscent of how MPI-IO partitions files. So this section may be thought of as a preparation to MPI-IO as well.

Let me begin by reminding you about the Coulomb law. If you have
two electrically charged particles, with charges *q*_{1} and *q*_{2}, then the force
with which particle 2 acts on particle 1 is given by

where is the dialectric constant of vacuum and vector

The force with which particle 1 acts on particle 2 is the opposite to
**F**_{12}, i.e.,

Sometimes equation (5.4) is printed without the minus in front of . Whether the minus should or should not be there depends on the definitions ofF_{12}andr_{12}. Ifr_{12}is the vector that points from particle 1 to particle 2, i.e.,r_{2}-r_{1}, and ifF_{12}is the force with which particle 2 acts on particle 1, then the minus should be there. Physics is one of these somewhat troubling disciplines, where you need to understand what happens and where you need to be very precise about what is what, otherwise it's easy to get confused.

Consider *N* particles of various charges scattered at random in some
region of space. In order to evaluate the total force that acts on
particle number *i* we have to evaluate the sum:

This sum has

We are going to distribute the computation over *n* processes by making
each process evaluate the force for *N*/*n* particles. Each process is
therefore going to evaluate
*N*/*n* (*N* - 1) terms, which may result
in considerable speed up of the computation for a sufficiently
large value of *n*.
In particular, if we could make *n* = *N*, the computation would scale
as
instead of
.
This is how nature
goes about ``parallelizing'' this problem. You can think of each
particle as being a separate processor that calculates its own evolution.

Within this example program we are going to push all *N* particles
for 20 short time steps using a very simplistic numerical procedure
that corresponds to the following equations of motion for particle *i*:

We can always choose to use such time units in our computation that

We are going to discretize the equations of motion by replacing d