简体   繁体   中英

Multi-threading molecular simulations in C++

I am developing a molecular dynamics simulation code in C++, which essentially takes atom positions and other properties as input and simulates their motion under Newton's laws of motion. The core algorithm uses what's called the Velocity Verlet scheme and looks like:

//  iterate through time (k=[1,#steps])
double Dt = 0.002; // time step
double Ttot = 1.0; // total time
double halfDt = Dt/2.0;

for (int k = 1; k*Dt <= Ttot; k++){
    for (int i = 0; i < number_particles; i++)
        vHalf[i] = p[i].velocity + F[i]*halfDt; // step 1

    for (int i = 0; i < number_particles; i++)
        p[i].position += vHalf[i]*Dt; // step 2

    for (int i = 0; i < number_particles; i++)
        F[i] = Force(p,i); // recalculate force on all particle i's

    for (int i = 0; i < number_particles; i++)
        p[i].velocity = vHalf[i] + F[i]*halfDt; // step 3
}

Where p is an array of class objects which store things like particle position, velocity, mass, etc. and Force is a function that calculates the net force on a particle using something like Lennard-Jones potential.

My question regards the time required to complete the calculation; all of my subroutines are optimized in terms of crunching numbers (eg using x*x*x to raise to the third power instead of pow(x,3) ), but the main issue is the time loop will often be performed for millions of iterations and there are typically close to a million particles. Is there any way to implement this algorithm using multi-threading? From my understanding, multi-threading essentially opens another stream of data to and from a CPU core, which would allow me to run two different simulations at the same time; I would like to use multi-threading to make just one of these simulations run faster

I'd recommend using OpenMP .

Your specific use case is trivially parallelizable. Prallelization should be as simple as:

double Dt = 0.002; // time step
double Ttot = 1.0; // total time
double halfDt = Dt/2.0;

for (int k = 1; k*Dt <= Ttot; k++){

    #pragma omp parallel for
    for (int i = 0; i < number_particles; i++)
        vHalf[i] = p[i].velocity + F[i]*halfDt; // step 1
        p[i].position += vHalf[i]*Dt; // step 2

    #pragma omp parallel for
    for (int i = 0; i < number_particles; i++)
        F[i] = Force(p,i); // recalculate force on all particle i's    
        p[i].velocity = vHalf[i] + F[i]*halfDt; // step 3
}

Most popular compilers and platforms have support for OpenMP.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM