Adding Components

This tutorial builds on Turorial 1. We can add various components to the system for the purpose of, for example, changing the thermodynamic ensemble sampled by the system. A component is anything that we can add to the main loop that operates on the system. This is analogous to the "fix" functionality in LAMMPS. To add a component, we use the AddSimulationComponent? member function.

#include <glotzilla++.h>

class LennardJonesSystem : public MdIntegrator
{
   public:
      LennardJonesSystem()
      {                 
         mInitialConditions = new MdInitializer;
                 
         InitializeParticles();
         mInitialConditions -> SetInteraction(new LennardJones);
         mInitialConditions -> SetForceRoutine(new VerletForce);
         mInitialConditions -> SetBoundaryConditions(new PeriodicBoundary(11));
         mInitialConditions -> SetMoveRoutine(new VerletMove);  
         mInitialConditions -> SetMoveRoutine(new VerletMove);

         //start additional code
        mThermostat = new BerendsenThermostat;
        mInitialConditions -> AddSimulationComponent(mThermostat);
        //end additional code
        
         InitializeSystem(mInitialConditions);
      }
      
       //start additional code
       void SetTemperature(double temperature)
       {
          mThermostat -> SetTemperature(temperature);
       }
       //end additional code
          
   private:
      void InitializeParticles()
      {
         ipstream particle_pipe("randbox -n=512 -r=-5,5,-5,5,-5,5 -m=1.0 -i=1000000");

         vec_t x;         
         while(particle_pipe >> x)
         {
            MdPointParticle *p = new MdPointParticle;
            p -> SetPosition(x);
            mInitialConditions -> AddParticle(p);
         }
         particle_pipe.close();
      }

      MdInitializer *mInitialConditions;

      //start additional code
      BerendsenThermostat *mThermostat;
      //end end additional code
};

int main(int argc, char ** argv) 
{
   LennardJonesSystem my_simulation;
   opstream my_pipe("vis3d -n=\"Lennard Jones System\"");

   my_simulation.SetTemperature(3.0);
   
   for(int timesteps=0; timesteps<100000; timesteps++)
   {
          if(timesteps == 1000)
             my_simulation.SetTemperature(0.25);

      if(timesteps % 5 == 0)
      {
             //the following line prints the timesteps in the visualizer
             my_pipe << "T 10 10 \"timesteps : " << timesteps << "\" -\n";
             my_simulation.PrintVisual(my_pipe);
      }

          my_simulation ++;
   }

   my_pipe.close();
   return 0;
}

Here, we have declared a BerendsenThermostat component, and added it to the system in the constructor. We have also added the member function

void SetTemperature(double temperature)
{
   mThermostat -> SetTemperature(temperature);
}

Whenever the SetTemperature? function is called, the BerendsenThermostat -> SetTemperature? member function is called, which changes the temperature on the thermostat, which in turn operates on the system. We do this in "main" using the call

my_simulation.SetTemperature(3.0);

which initializes the temperature to 3.0. We later change the temperature to 0.25 after 1000 timesteps.