diff --git a/ABACUS.develop/source/Makefile.Objects b/ABACUS.develop/source/Makefile.Objects index 27e60059ce..d241353e70 100644 --- a/ABACUS.develop/source/Makefile.Objects +++ b/ABACUS.develop/source/Makefile.Objects @@ -53,9 +53,10 @@ chi0_hilbert.o\ chi0_standard.o\ epsilon0_pwscf.o\ epsilon0_vasp.o\ -md.o\ -mdNVE.o\ -mdNVT.o\ +MD_basic.o\ +MD_thermo.o\ +MD_fire.o\ +MD_func.o\ exx_lip.o\ soc.o\ to_wannier90.o \ diff --git a/ABACUS.develop/source/input.cpp b/ABACUS.develop/source/input.cpp index 25fa136250..a56a80ca24 100644 --- a/ABACUS.develop/source/input.cpp +++ b/ABACUS.develop/source/input.cpp @@ -292,27 +292,6 @@ void Input::Default(void) md_tstep=1; //reduec md_delt every md_tstep step. md_delt=1.0; */ - //md and related parameters(added by zheng da ye) - md_mdtype=1; - md_tauthermo=0; - md_taubaro=0; - md_dt=-1; - md_nresn=3; - md_nyosh=3; - md_qmass=1; - md_tfirst=-1; //kelvin - md_tlast=md_tfirst; - md_dumpmdfred=1; - md_mdoutpath="mdoutput"; - md_domsd=0; - md_domsdatom=0; - md_rstmd=0; - md_outputstressperiod=1; - md_fixtemperature=1; - md_ediff=1e-4; - md_ediffg=1e-3; - md_msdstartTime=1; - //end of zhengdaye's add. /* //---------------------------------------------------------- // vdwD2 //Peize Lin add 2014-03-31, update 2015-09-30 @@ -1128,79 +1107,59 @@ bool Input::Read(const string &fn) //added begin by zheng daye else if (strcmp("md_mdtype",word) == 0) { - read_value(ifs, md_mdtype); + read_value(ifs, mdp.mdtype); } - else if (strcmp("md_tauthermo",word) == 0) + else if (strcmp("NVT_tau",word) == 0) { - read_value(ifs, md_tauthermo); + read_value(ifs, mdp.NVT_tau); } - else if (strcmp("md_taubaro",word) == 0) + else if (strcmp("NVT_control",word) == 0) { - read_value(ifs,md_taubaro ); + read_value(ifs,mdp.NVT_control ); } else if (strcmp("md_dt",word) == 0) { - read_value(ifs, md_dt); + read_value(ifs, mdp.dt); } - else if (strcmp("md_nresn",word) == 0) + else if (strcmp("mnhc",word) == 0) { - read_value(ifs,md_nresn ); - } - else if (strcmp("md_nyosh",word) == 0) - { - read_value(ifs, md_nyosh); + read_value(ifs,mdp.MNHC ); } else if (strcmp("md_qmass",word) == 0) { - read_value(ifs,md_qmass ); + read_value(ifs,mdp.Qmass ); } else if (strcmp("md_tfirst",word) == 0) { - read_value(ifs, md_tfirst); + read_value(ifs, mdp.tfirst); } else if (strcmp("md_tlast",word) == 0) { - read_value(ifs,md_tlast ); + read_value(ifs,mdp.tlast ); } else if (strcmp("md_dumpmdfred",word) == 0) { - read_value(ifs, md_dumpmdfred); + read_value(ifs, mdp.recordFreq); } else if (strcmp("md_mdoutpath",word) == 0) { - read_value(ifs,md_mdoutpath ); - } - else if (strcmp("md_domsd",word) == 0) - { - read_value(ifs, md_domsd); - } - else if (strcmp("md_domsdatom",word) == 0) - { - read_value(ifs, md_domsdatom); + read_value(ifs,mdp.mdoutputpath ); } else if (strcmp("md_rstmd",word) == 0) { - read_value(ifs,md_rstmd ); - } - else if (strcmp("md_outputstressperiod",word) == 0) - { - read_value(ifs,md_outputstressperiod ); + read_value(ifs,mdp.rstMD ); } else if (strcmp("md_fixtemperature",word) == 0) { - read_value(ifs,md_fixtemperature ); + read_value(ifs,mdp.fixTemperature ); } else if (strcmp("md_ediff",word) == 0) { - read_value(ifs,md_ediff ); + read_value(ifs,mdp.ediff ); } else if (strcmp("md_ediffg",word) == 0) { - read_value(ifs,md_ediffg ); - } - else if (strcmp("md_msdstarttime",word) == 0) - { - read_value(ifs,md_msdstartTime ); + read_value(ifs,mdp.ediffg ); } //added by zheng daye //---------------------------------------------------------- @@ -2087,7 +2046,7 @@ void Input::Bcast() Parallel_Common::bcast_int( selinv_niter); /* // mohan add 2011-11-07 - Parallel_Common::bcast_double( md_dt ); + Parallel_Common::bcast_double( mdp.dt ); Parallel_Common::bcast_int( md_restart ); Parallel_Common::bcast_double( md_tolv ); Parallel_Common::bcast_string( md_thermostat ); @@ -2096,25 +2055,20 @@ void Input::Bcast() Parallel_Common::bcast_double( md_delt ); */ //zheng daye add 2014/5/5 - Parallel_Common::bcast_int(md_mdtype); - Parallel_Common::bcast_double(md_tauthermo); - Parallel_Common::bcast_double(md_taubaro); - Parallel_Common::bcast_double(md_dt); - Parallel_Common::bcast_int(md_nresn); - Parallel_Common::bcast_int(md_nyosh); - Parallel_Common::bcast_double(md_qmass); - Parallel_Common::bcast_double(md_tfirst); - Parallel_Common::bcast_double(md_tlast); - Parallel_Common::bcast_int(md_dumpmdfred); - Parallel_Common::bcast_string(md_mdoutpath); - Parallel_Common::bcast_bool(md_domsd); - Parallel_Common::bcast_bool(md_domsdatom); - Parallel_Common::bcast_int(md_rstmd); - Parallel_Common::bcast_int(md_outputstressperiod); - Parallel_Common::bcast_int(md_fixtemperature); - Parallel_Common::bcast_double(md_ediff); - Parallel_Common::bcast_double(md_ediffg); - Parallel_Common::bcast_int(md_msdstartTime); + Parallel_Common::bcast_int(mdp.mdtype); + Parallel_Common::bcast_double(mdp.NVT_tau); + Parallel_Common::bcast_int(mdp.NVT_control); + Parallel_Common::bcast_double(mdp.dt); + Parallel_Common::bcast_int(mdp.MNHC); + Parallel_Common::bcast_double(mdp.Qmass); + Parallel_Common::bcast_double(mdp.tfirst); + Parallel_Common::bcast_double(mdp.tlast); + Parallel_Common::bcast_int(mdp.recordFreq); + Parallel_Common::bcast_string(mdp.mdoutputpath); + Parallel_Common::bcast_int(mdp.rstMD); + Parallel_Common::bcast_int(mdp.fixTemperature); + Parallel_Common::bcast_double(mdp.ediff); + Parallel_Common::bcast_double(mdp.ediffg); /* // Peize Lin add 2014-04-07 Parallel_Common::bcast_bool( vdwD2 ); Parallel_Common::bcast_double( vdwD2_scaling ); @@ -2483,10 +2437,10 @@ void Input::Check(void) //deal with input parameters , 2019-04-30 if(basis_type == "pw" ) WARNING_QUIT("Input::Check","calculate = MD is only availble for LCAO."); - if(md_dt == -1) WARNING_QUIT("Input::Check","time interval of MD calculation should be set!"); - if(md_tfirst == -1) WARNING_QUIT("Input::Check","temperature of MD calculation should be set!"); - if(md_tlast == -1) md_tlast = md_tfirst; - if(md_tfirst!=md_tlast) + if(mdp.dt < 0) WARNING_QUIT("Input::Check","time interval of MD calculation should be set!"); + if(mdp.tfirst < 0) WARNING_QUIT("Input::Check","temperature of MD calculation should be set!"); + if(mdp.tlast < 0.0) mdp.tlast = mdp.tfirst; + if(mdp.tfirst!=mdp.tlast) { ifstream file1; file1.open("ChangeTemp.dat"); @@ -2496,7 +2450,7 @@ void Input::Check(void) file.open("ChangeTemp.dat"); for(int ii=0;ii<30;ii++) { - file< +#include "src_pw/MD_parameters.h" using namespace std; class Input @@ -244,7 +245,7 @@ class Input // molecular dynamics // added by Daye Zheng //========================================================== - int md_mdtype; //choose ensemble +/* int md_mdtype; //choose ensemble double md_tauthermo; double md_taubaro; double md_dt; //time step @@ -262,7 +263,8 @@ class Input int md_fixtemperature; //period to change temperature double md_ediff; //parameter for constraining total energy change double md_ediffg; //parameter for constraining max force change - int md_msdstartTime; //choose which step that msd be calculated + int md_msdstartTime; //choose which step that msd be calculated */ + MD_parameters mdp; //========================================================== // vdw diff --git a/ABACUS.develop/source/src_io/print_info.cpp b/ABACUS.develop/source/src_io/print_info.cpp index 515cca97db..993816b4e3 100644 --- a/ABACUS.develop/source/src_io/print_info.cpp +++ b/ABACUS.develop/source/src_io/print_info.cpp @@ -37,16 +37,17 @@ void Print_Info::setup_parameters(void) cout << " ---------------------------------------------------------" << endl; - if(INPUT.md_mdtype ==1 || INPUT.md_mdtype==2) + if(INPUT.mdp.mdtype ==1 || INPUT.mdp.mdtype==2) { cout << " ENSEMBLE : " << "NVT" << endl; + cout << " Qmass for NVT(a.u.) : " << INPUT.mdp.Qmass/6.02/9.109*1e5 << endl; } - else if(INPUT.md_mdtype==0) + else if(INPUT.mdp.mdtype==0) { cout << " ENSEMBLE : " << "NVE" << endl; } - cout << " Qmass for NVT(a.u.) : " << INPUT.md_qmass/6.02/9.109*1e5 << endl; - cout << " Time interval(fs) : " << INPUT.md_dt << endl; + + cout << " Time interval(fs) : " << INPUT.mdp.dt << endl; } cout << " ---------------------------------------------------------" << endl; diff --git a/ABACUS.develop/source/src_io/write_input.cpp b/ABACUS.develop/source/src_io/write_input.cpp index 5db6d49b03..877a6cd7de 100644 --- a/ABACUS.develop/source/src_io/write_input.cpp +++ b/ABACUS.develop/source/src_io/write_input.cpp @@ -141,22 +141,20 @@ void Input::Print(const string &fn)const OUTP(ofs,"selinv_niter",selinv_niter,"max number of steps to update mu"); ofs << "\n#Parameters (10.Molecular dynamics)" << endl; - OUTP(ofs,"md_mdtype",md_mdtype,"choose ensemble"); - OUTP(ofs,"md_dt",md_dt,"time step"); - OUTP(ofs,"md_nresn",md_nresn,"parameter during integrater"); - OUTP(ofs,"md_nyosh",md_nyosh,"parameter during integrater"); - OUTP(ofs,"md_qmass",md_qmass,"mass of thermostat"); - OUTP(ofs,"md_tfirst",md_tfirst,"temperature first"); - OUTP(ofs,"md_tlast",md_tlast,"temperature last"); - OUTP(ofs,"md_dumpmdfred",md_dumpmdfred,"The period to dump MD information for monitoring and restarting MD"); - OUTP(ofs,"md_mdoutpath",md_mdoutpath,"output path of md"); - OUTP(ofs,"md_domsd",md_domsd,"whether compute "); - OUTP(ofs,"md_domsdatom",md_domsdatom,"whether compute msd for each atom"); - OUTP(ofs,"md_rstmd",md_rstmd,"whether restart"); - OUTP(ofs,"md_fixtemperature",md_fixtemperature,"period to change temperature"); - OUTP(ofs,"md_ediff",md_ediff,"parameter for constraining total energy change"); - OUTP(ofs,"md_ediffg",md_ediffg,"parameter for constraining max force change"); - OUTP(ofs,"md_msdstarttime",md_msdstartTime,"choose which step that msd be calculated"); + OUTP(ofs,"md_mdtype",mdp.mdtype,"choose ensemble"); + OUTP(ofs,"md_dt",mdp.dt,"time step"); + OUTP(ofs,"mnhc",mdp.MNHC,"number of Nose-Hoover chains"); + OUTP(ofs,"md_qmass",mdp.Qmass,"mass of thermostat"); + OUTP(ofs,"md_tfirst",mdp.tfirst,"temperature first"); + OUTP(ofs,"md_tlast",mdp.tlast,"temperature last"); + OUTP(ofs,"md_dumpmdfred",mdp.recordFreq,"The period to dump MD information for monitoring and restarting MD"); + OUTP(ofs,"md_mdoutpath",mdp.mdoutputpath,"output path of md"); + OUTP(ofs,"md_rstmd",mdp.rstMD,"whether restart"); + OUTP(ofs,"md_fixtemperature",mdp.fixTemperature,"period to change temperature"); + OUTP(ofs,"md_ediff",mdp.ediff,"parameter for constraining total energy change"); + OUTP(ofs,"md_ediffg",mdp.ediffg,"parameter for constraining max force change"); + OUTP(ofs,"NVT_tau",mdp.NVT_tau,"parameter for adjust effect of thermostat"); + OUTP(ofs,"NVT_control",mdp.NVT_control,"choose which thermostat used in NVT ensemble"); ofs << "\n#Parameters (11.Efield)" << endl; OUTP(ofs,"efield",efield,"add electric field"); diff --git a/ABACUS.develop/source/src_ions/variable_cell.cpp b/ABACUS.develop/source/src_ions/variable_cell.cpp index 009e700837..7ba80704cc 100644 --- a/ABACUS.develop/source/src_ions/variable_cell.cpp +++ b/ABACUS.develop/source/src_ions/variable_cell.cpp @@ -58,7 +58,7 @@ void Variable_Cell::final_calculation_after_vc(void) cout<<" -----------------------------------------------------------------"<** c, compl double delta_t; // delta_t = 0.2; //identity: fs; ComplexMatrix Numerator(NLOCAL,NLOCAL); - Numerator = Idmat - 0.5*INPUT.md_dt*41.34*Denominator; - Denominator = Idmat + 0.5*INPUT.md_dt*41.34*Denominator; + Numerator = Idmat - 0.5*INPUT.mdp.dt*41.34*Denominator; + Denominator = Idmat + 0.5*INPUT.mdp.dt*41.34*Denominator; int info; int lwork=3*NLOCAL-1; //tmp @@ -368,8 +368,8 @@ void ELEC_evolve::using_LAPACK_complex_2(const int &ik, complex** c, com } double delta_t; ComplexMatrix Numerator(NLOCAL,NLOCAL); - Numerator = Idmat - 0.5*INPUT.md_dt*41.34*Denominator; - Denominator = Idmat + 0.5*INPUT.md_dt*41.34*Denominator; + Numerator = Idmat - 0.5*INPUT.mdp.dt*41.34*Denominator; + Denominator = Idmat + 0.5*INPUT.mdp.dt*41.34*Denominator; int info; int lwork=3*NLOCAL-1; //tmp diff --git a/ABACUS.develop/source/src_lcao/FORCE_STRESS.h b/ABACUS.develop/source/src_lcao/FORCE_STRESS.h index d27cb86bcb..acfe68c784 100644 --- a/ABACUS.develop/source/src_lcao/FORCE_STRESS.h +++ b/ABACUS.develop/source/src_lcao/FORCE_STRESS.h @@ -16,6 +16,7 @@ class Force_Stress_LCAO friend void Input_Conv::Convert(); friend class Update_input; friend class LOOP_ions; + friend class MD_func; public : diff --git a/ABACUS.develop/source/src_lcao/LCAO_evolve.cpp b/ABACUS.develop/source/src_lcao/LCAO_evolve.cpp index 21b0971822..286095aaa8 100644 --- a/ABACUS.develop/source/src_lcao/LCAO_evolve.cpp +++ b/ABACUS.develop/source/src_lcao/LCAO_evolve.cpp @@ -150,8 +150,8 @@ void Evolve_LCAO_Matrix::using_LAPACK_complex(const int &ik, complex** c double delta_t; // delta_t = 0.2; //identity: fs; ComplexMatrix Numerator(NLOCAL,NLOCAL); - Numerator = Idmat - 0.5*INPUT.md_dt*41.34*Denominator; - Denominator = Idmat + 0.5*INPUT.md_dt*41.34*Denominator; + Numerator = Idmat - 0.5*INPUT.mdp.dt*41.34*Denominator; + Denominator = Idmat + 0.5*INPUT.mdp.dt*41.34*Denominator; int info; int lwork=3*NLOCAL-1; //tmp diff --git a/ABACUS.develop/source/src_lcao/run_md.cpp b/ABACUS.develop/source/src_lcao/run_md.cpp index 4fee78666d..28bcae3e9c 100644 --- a/ABACUS.develop/source/src_lcao/run_md.cpp +++ b/ABACUS.develop/source/src_lcao/run_md.cpp @@ -13,7 +13,6 @@ #include "ELEC_scf.h" #include "src_global/sltk_atom_arrange.h" #include "src_pw/vdwd2.h" -#include "src_pw/vdwd3.h" Run_MD::Run_MD() {} @@ -88,20 +87,8 @@ void Run_MD::opt_ions(void) LCM.allocate(); } - mdtype= INPUT.md_mdtype;//control md - - // NVT ensemble - if(mdtype==1||mdtype==2) - { - MDNVT.md_allocate(); - MDNVT.initMD(); - } - // NVE ensemble - else if(mdtype==0) - { - MDNVE.md_allocate(); - MDNVE.initMD(); - } + MD_basic mdb(INPUT.mdp, ucell); + int mdtype = INPUT.mdp.mdtype; this->istep = 1; int force_step = 1; @@ -115,10 +102,7 @@ void Run_MD::opt_ions(void) if(OUT_LEVEL=="ie" || OUT_LEVEL=="m") { cout << " ---------------------------------------------------------" << endl; - if(mdtype==1||mdtype==2) - { - cout<<" Molecular Dynamics (NVT) STEP "<< MDNVT.step_rst + istep<1) final_scf(); + // mohan update 2021-02-10 hm.orb_con.clear_after_ions(UOT, ORB, INPUT.out_descriptor); @@ -210,190 +196,6 @@ void Run_MD::opt_ions(void) return; } -//bool Run_MD::force_stress(void) -bool Run_MD::force_stress(const int &istep, int &force_step, int &stress_step) -{ - TITLE("Run_MD","force_stress"); - if(!FORCE && !STRESS) - { - return 1; - } - timer::tick("Run_MD","force_stress",'D'); - matrix fcs; - matrix scs; - Force_Stress_LCAO FSL; - FSL.allocate (); - FSL.getForceStress(FORCE, STRESS, TEST_FORCE, TEST_STRESS, fcs, scs); - //-------------------------------------------------- - // only forces are needed, no stresses are needed - //-------------------------------------------------- - if(FORCE && !STRESS) - { - -#ifdef __MPI //2015-10-01, xiaohui - atom_arrange::delete_vector( SEARCH_RADIUS ); -#endif //2015-10-01, xiaohui - - if(CALCULATION=="relax") - { - IMM.cal_movement(istep, istep, fcs, en.etot); - - if(IMM.get_converged() || (istep==NSTEP)) - { - return 1; // 1 means converged - } - else // ions are not converged - { - CE.update_istep(istep); - CE.extrapolate_charge(); - - if(pot.extra_pot=="dm") - { - } - else - { - pot.init_pot( istep, pw.strucFac ); - } - } - return 0; - } - else - { - return 1; - } - - // mohan update 2013-04-11 - // setup the structure factor - // and do the density extraploation. - // for both ionic iteratoin and - // force calculations. - - //xiaohui modify 2014-08-09 - //pw.setup_structure_factor(); - - // charge extrapolation if istep>0. - //xiaohui modify 2014-08-09 - //CE.extrapolate_charge(); - -/*xiaohui modify 2014-08-09 - if(pot.extra_pot==4) - { - // done after grid technique. - } - else - { - pot.init_pot( istep ); - } -xiaohui modify 2014-08-09*/ - } - - static bool converged_force = false; - static bool converged_stress = false; - - if(!FORCE&&STRESS) - { - -#ifdef __MPI - atom_arrange::delete_vector( SEARCH_RADIUS ); -#endif - if(CALCULATION=="cell-relax") - { - LCM.cal_lattice_change(stress_step, scs, en.etot); - converged_stress = LCM.get_converged(); - if(converged_stress) - { - return 1; - } - else - { - Variable_Cell::init_after_vc(); - pot.init_pot(stress_step, pw.strucFac); - - ++stress_step; - return 0; - } - } - else - { - return 1; - } - } - - if(FORCE&&STRESS) - { - -//#ifdef __MPI - atom_arrange::delete_vector( SEARCH_RADIUS ); -//#endif - - //if(CALCULATION=="relax") IMM.cal_movement(istep, FL.fcs, en.etot); - if(CALCULATION=="relax" || CALCULATION=="cell-relax") - { - IMM.cal_movement(istep, force_step, fcs, en.etot); - - if(IMM.get_converged()) - { - force_step = 1; - - - if(CALCULATION=="cell-relax") - { - LCM.cal_lattice_change(stress_step, scs, en.etot); - converged_stress = LCM.get_converged(); - if(converged_stress) - { - return 1; - } - else - { - Variable_Cell::init_after_vc(); - pot.init_pot(stress_step, pw.strucFac); - - ++stress_step; - return 0; - } - } - else - { - return 1; - } - -#ifdef __MPI - //atom_arrange::delete_vector( SEARCH_RADIUS ); -#endif - } - else - { -#ifdef __MPI - //atom_arrange::delete_vector( SEARCH_RADIUS ); -#endif - //CE.istep = istep; - CE.update_istep(force_step); - CE.extrapolate_charge(); - - if(pot.extra_pot=="dm")//xiaohui modify 2015-02-01 - { - // done after grid technique. - } - else - { - pot.init_pot( istep, pw.strucFac ); - } - ++force_step; - return 0; - } - } - else - { - return 1; - } - } - - return 0; - - timer::tick("Run_MD","force_stress",'D'); -} - void Run_MD::final_scf(void) { TITLE("Run_MD","final_scf"); @@ -453,18 +255,15 @@ void Run_MD::final_scf(void) Vdwd3 vdwd3(ucell,vdwd3_para); vdwd3.cal_energy(); en.evdw = vdwd3.get_energy(); - } + } ELEC_scf es; es.scf(0); - if(CALCULATION=="scf" || CALCULATION=="relax") - { - ofs_running << "\n\n --------------------------------------------" << endl; - ofs_running << setprecision(16); - ofs_running << " !FINAL_ETOT_IS " << en.etot * Ry_to_eV << " eV" << endl; - ofs_running << " --------------------------------------------\n\n" << endl; - } + ofs_running << "\n\n --------------------------------------------" << endl; + ofs_running << setprecision(16); + ofs_running << " !FINAL_ETOT_IS " << en.etot * Ry_to_eV << " eV" << endl; + ofs_running << " --------------------------------------------\n\n" << endl; return; } diff --git a/ABACUS.develop/source/src_lcao/run_md.h b/ABACUS.develop/source/src_lcao/run_md.h index 96e7b42dc8..93c17b5c39 100644 --- a/ABACUS.develop/source/src_lcao/run_md.h +++ b/ABACUS.develop/source/src_lcao/run_md.h @@ -4,9 +4,7 @@ #include "LOOP_elec.h" #include "../src_ions/ions_move_methods.h" #include "../src_pw/charge_extra.h" -#include "../src_pw/md.h" -#include "../src_pw/mdNVT.h" -#include "../src_pw/mdNVE.h" +#include "../src_pw/MD_basic.h" #include "../src_ions/lattice_change_methods.h" class Run_MD @@ -22,10 +20,6 @@ class Run_MD void opt_cell(void); void opt_ions(void); - //2014-06-06, xiaohui - mdnvt MDNVT ; - mdNVE MDNVE ; - private: Ions_Move_Methods IMM; @@ -33,16 +27,11 @@ class Run_MD //bool force_stress(void); Lattice_Change_Methods LCM; - bool force_stress(const int &istep, int &force_step, int &stress_step); - int istep; // electron charge density extropolation method Charge_Extra CE; - //choose md ensemble, zheng daye - int mdtype; - void final_scf(void); }; diff --git a/ABACUS.develop/source/src_pw/MD_basic.cpp b/ABACUS.develop/source/src_pw/MD_basic.cpp new file mode 100644 index 0000000000..01a3ee009d --- /dev/null +++ b/ABACUS.develop/source/src_pw/MD_basic.cpp @@ -0,0 +1,606 @@ +#include "src_pw/MD_basic.h" +#include "src_pw/global.h" + +//define in MD_basic.h +//class MD_basic + +const double MD_basic::fundamentalTime = 2.418884326505e-17; + +MD_basic::MD_basic(MD_parameters& MD_para_in, UnitCell_pseudo &unit_in): + mdp(MD_para_in), + ucell(unit_in) +{ + mdp.dt=mdp.dt/fundamentalTime/1e15; + temperature_=mdp.tfirst/3.1577464e5; + + + //other parameter default + outputstressperiod_ = 1 ;// The period to output stress +// ucell.nat=ucell.nat; +// ntype=ucell.ntype; + step_rst_=0; + step_=0; +// ucell.latvec=ucell.latvec; + + vel=new Vector3[ucell.nat]; + cart_change=new Vector3[ucell.nat]; + tauDirectChange=new Vector3[ucell.nat]; + allmass=new double[ucell.nat]; + ionmbl=new Vector3[ucell.nat]; + force=new Vector3[ucell.nat]; + + energy_=en.etot/2; + + //MD starting setup + if(!mdp.rstMD){ + nfrozen_ = mdf.getMassMbl(ucell, allmass, ionmbl); + //mdf.gettauDirectChange(ucell, tauDirectChange); + //A fresh new MD: Do not restart MD + mdf.InitVelocity(ucell.nat, temperature_, fundamentalTime, allmass, vel) ; + // Initialize thermostat, and barostat + + } + else{ + nfrozen_ = mdf.getMassMbl(ucell, allmass, ionmbl); + //mdf.gettauDirectChange(ucell, tauDirectChange); + mdf.InitVelocity(ucell.nat, temperature_, fundamentalTime, allmass, vel) ; + if(!mdf.RestartMD(ucell.nat, vel, step_rst_)){ + cout<<"error in restart MD!"<update_half_velocity(); + } + else + { + this->update_half_velocity(); + + twiceKE=mdf.GetAtomKE(ucell.nat, vel, allmass); + twiceKE = 2 * twiceKE; + if(mdp.NVT_control==1) + { + hamiltonian = mdt.NHChamiltonian( + twiceKE/2, + energy_, + temperature_, + nfrozen_); + } + else hamiltonian = mdf.Conserved(twiceKE/2, energy_, ucell.nat-nfrozen_); + //Note: side scheme position before + //Now turn to middle scheme. + this->update_half_velocity(); + } + + // Update the Non-Wrapped cartesion coordinates + if(mdp.mdtype==2) mdf.scalevel(ucell.nat, nfrozen_, temperature_, vel, allmass);//choose velocity scaling method + + update_half_direct(1); + + mdt.Integrator(mdp.NVT_control, temperature_, vel, allmass);//thermostat interact with velocity + twiceKE=mdf.GetAtomKE(ucell.nat, vel, allmass); + twiceKE = 2 * twiceKE; + + update_half_direct(0); + + // Calculate the maximal velocities. + // The step in fractional coordinates + double maxStep = 0; + for(int ii=0;iimaxStep) + { + maxStep = pow(vel[ii].x,2)+pow(vel[ii].y,2)+pow(vel[ii].z,2); + } + } + getTaudUpdate(); + + //save the atom position change to DFT module + save_output_position(); + maxStep = sqrt(maxStep)*mdp.dt; + + if (!MY_RANK){ + ofs_running<update_half_velocity(); + // (2) 2nd step of Verlet-Velocity + // Update the Non-Wrapped cartesion coordinate + twiceKE = mdf.GetAtomKE(ucell.nat, vel, allmass); + twiceKE = 2 * twiceKE; + if(step_!=1||mdp.rstMD==1)this->update_half_velocity(); + update_half_direct(1); + update_half_direct(0); + // Calculate the maximal velocities. + // The step in fractional coordinates + double maxStep = 0; + for(int i = 0;i< ucell.nat;i++) + { + if((pow(vel[i].x,2.0)+pow(vel[i].y,2.0)+pow(vel[i].z,2.0))>maxStep) + { + maxStep = pow(vel[i].x,2.0)+pow(vel[i].y,2.0)+pow(vel[i].z,2.0); + } + } + getTaudUpdate(); + save_output_position(); + maxStep = sqrt(maxStep)*mdp.dt; + + + // calculate the conserved quantity during MD + double hamiltonian = mdf.Conserved(twiceKE/2, energy_, ucell.nat-nfrozen_); + + cout<< setprecision (9)<update_half_velocity(); + + // (2) 2nd step of Verlet-Velocity + // Update the Non-Wrapped cartesion coordinate + twiceKE = mdf.GetAtomKE(ucell.nat, vel, allmass); + twiceKE = 2 * twiceKE; + if(step_!=1)this->update_half_velocity(); + + double largest_grad_FIRE = 0.0; + for(int i=0;imaxStep) + { + maxStep = pow(vel[i].x,2.0)+pow(vel[i].y,2.0)+pow(vel[i].z,2.0); + } + } + getTaudUpdate(); + + save_output_position(); + maxStep = sqrt(maxStep)*mdp.dt; + + double hamiltonian = mdf.Conserved(twiceKE/2, energy_, ucell.nat-nfrozen_); + + + + + // Output the message to the screen. + oldEtot_=energy_; + + cout<<"(NVE): this step finished."<step_; +} + +//output pressure of total MD system, P = tr(stress) + P_kin +void MD_basic::outStressMD(const matrix& stress, const double& twiceKE) +{ + ofs_running<<"output Pressure for check!"< fracStep; + for(int ii=0;ii *vel;// velocity of each atom, unit is a.u. + double *allmass; //mass of each atom + Vector3 *force; //force of each atom + matrix stress; //stress for this lattice + Vector3 *ionmbl; //if frozen of each atom + Vector3 *tauDirectChange; //change of dirac coord of atoms + Vector3 *cart_change; //cartensian coord of atoms, *not* wrapped + + //repete code + void update_half_velocity(); + void update_half_direct(const bool is_restart); + void save_output_position(); + void outStressMD(const matrix& stress, const double& twiceKE); + void getTaudUpdate(); + + +}; + +#endif \ No newline at end of file diff --git a/ABACUS.develop/source/src_pw/MD_fire.cpp b/ABACUS.develop/source/src_pw/MD_fire.cpp new file mode 100644 index 0000000000..91a1c9f10c --- /dev/null +++ b/ABACUS.develop/source/src_pw/MD_fire.cpp @@ -0,0 +1,68 @@ +#include "src_pw/MD_fire.h" + +MD_fire::MD_fire() +{ + dt_max=-1.0; + alpha_start=0.10; + alpha = alpha_start; + + finc=1.1; + fdec=0.5; + f_alpha=0.99; + N_min=4; + negative_count=0; +} + +void MD_fire::check_FIRE( + const int& numIon, + const Vector3const* force, + double& deltaT, + Vector3* vel) +{ + if(dt_max<0) dt_max = deltaT * 2.5; //initial dt_max + double P(0.0); + double sumforce(0.0); + double normvel(0.0); + + for(int iatom =0;iatom 0 ){ + negative_count +=1 ; + if(negative_count >=N_min) + { + deltaT=min(deltaT*finc,dt_max); + alpha= alpha *f_alpha; + } + } + else if( P<=0) + { + deltaT=deltaT*fdec; + negative_count = 0; + + for(int iatom=0; iatomconst* force, + double& deltaT, + Vector3* vel); + private: + double alpha_start ;//alpha_start begin + double alpha;//alpha begin + double finc;//finc begin + double fdec;//fdec begin + double f_alpha; + int N_min; + double dt_max;//dt_max + int negative_count;//Negative count +}; + +#endif \ No newline at end of file diff --git a/ABACUS.develop/source/src_pw/MD_func.cpp b/ABACUS.develop/source/src_pw/MD_func.cpp index 9905f14eed..9756d7b4a7 100644 --- a/ABACUS.develop/source/src_pw/MD_func.cpp +++ b/ABACUS.develop/source/src_pw/MD_func.cpp @@ -1,225 +1,85 @@ -#include "MD_func.h" - - - -void MD_func::initMD(){ - //parameter from input file - mdtype=INPUT.md_mdtype; - Qmass=INPUT.md_qmass/6.02/9.109*1e5; - dt=INPUT.md_dt/fundamentalTime/1e15; - temperature=INPUT.md_tfirst/3.1577464e5; - rstMD=INPUT.md_rstmd; - dumpmdfreq=INPUT.md_dumpmdfred; - fixTemperature=INPUT.md_fixtemperature; - ediff=INPUT.md_ediff; - ediffg=INPUT.md_ediffg; - mdoutputpath=INPUT.md_mdoutpath; - NVT_control = INPUT.md_nvtcontrol; - NVT_tau = INPUT.md_nvttau; - MNHC = INPUT.md_mnhc; - - - //other parameter default - outputstressperiod = 1 ;// The period to output stress - numIon=ucell.nat; - ntype=ucell.ntype; - step_rst=0; - ionlatvec=ucell.latvec; - - mdenergy=en.etot/2; - - //allocate for MD - this->md_allocate(); - - //MD starting setup - if(rstMD==0){ - connection0(); - connection1(); - //A fresh new MD: Do not restart MD - InitVelocity() ; - // Initialize thermostat, and barostat - - } - else if ( rstMD>0 ){ - connection0(); - connection1(); - InitVelocity() ; - if(!RestartMD()){ - cout<<"error in restart MD!"<=1;j--){ - for(int k=0;k* vel, int& step_rst) +{ + int error(0); double *vell=new double[numIon*3]; - double *cart=new double[numIon*3]; - double *dira=new double[numIon*3]; - double *nhcg=new double[numIon*3*MNHC]; - double *nhcp=new double[numIon*3*MNHC]; - double *nhce=new double[numIon*3*MNHC]; - if (!MY_RANK){ + if (!MY_RANK) + { stringstream ssc; - ssc << global_out_dir << "Restart_md.dat"; + ssc << global_readin_dir << "Restart_md.dat"; ifstream file(ssc.str().c_str()); - if(!file){ - cout<<"please ensure whether 'Restart_md.dat' exists"<>xLogS; - file.get(); - file.ignore(7, '\n'); - // file>>vLogS; - file.get(); - file.ignore(23, '\n'); - for(i = 0;i>vell[i]; + //---------------------------------------------------------- + // main parameters + //---------------------------------------------------------- + file.ignore(13, '\n');//read and assert number of atoms + int num; + file>>num; + if(num != numIon) + { + cout<<"please ensure whether 'Restart_md.dat' right!"<>cart[i]; + if (!error) + { + file.get(); + file.ignore(23, '\n');//read velocities + for(int i = 0;i>vell[i]; + } + file.get(); + file.ignore(6, '\n');//read start step of MD + file>>step_rst; + file.close(); } - file.get(); file.ignore(13, '\n'); - for(i=0;i>dira[i]; - }*/ - file.get(); - file.ignore(6, '\n'); - file>>step_rst; - file.close(); } -//2015-09-05, xiaohui +#ifdef __MPI + MPI_Bcast(&error,1,MPI_INT,0,MPI_COMM_WORLD); +#endif + if(error) + { + delete[] vell; + exit(0); + } #ifdef __MPI MPI_Bcast(&step_rst,1,MPI_INT,0,MPI_COMM_WORLD); MPI_Bcast(vell,numIon*3,MPI_DOUBLE,0,MPI_COMM_WORLD); #endif - for(i=0;i echo_md_restart.dat, for debug purpose. "<* vel) +{ //this function used for outputting the information of restart file bool pass; pass = 0; - if (dumpmdfreq==1||step==1||( dumpmdfreq > 1&& step%dumpmdfreq==0 ) ) + if (recordFreq==1||step==1||( recordFreq > 1&& step%recordFreq==0 ) ) pass =1; if (!pass) return; @@ -228,25 +88,18 @@ void MD_func::mstout(int step){ ssc << global_out_dir << "Restart_md.dat"; ofstream file(ssc.str().c_str()); file<<"MD_RESTART"<const* vel, const double const* allmass){ //--------------------------------------------------------------------------- // DESCRIPTION: // This function calculates the classical kinetic energy of a group of atoms. @@ -264,7 +117,12 @@ double MD_func::GetAtomKE(){ return ke; } -void MD_func::InitVelocity() +void MD_func::InitVelocity( + const int& numIon, + const double& temperature, + const double& fundamentalTime, + const double const* allmass, + Vector3* vel) { if(!MY_RANK){ //xiaohui add 2015-09-25 srand(time(0)); @@ -323,82 +181,7 @@ void MD_func::InitVelocity() return; } - -void MD_func::OutputMDHeader() -{ -//--------------------------------------------------- -// Output the Header for MD simulation -//--------------------------------------------------- - - // Set up extra output to ion optimizer / MD header - if (!MY_RANK) - out<<"Q ="<* ionmbl) +{ //some prepared information //mass and degree of freedom int ion=0; - nfrozen=0; - for(int it=0;it* force, matrix& stress_lcao) { //to call the force of each atom - int ion; - Force_LCAO FL; - FL.allocate (); - FL.start_force(); - for(ion=0;ion* force, matrix& stress_pw) +{ +//to call the force of each atom + matrix fcs;//temp force matrix + Forces ff; + ff.init(fcs); + for(int ion=0;ion=1.0) taudirac[ia].x -= 1.0; - if(taudirac[ia].y>=1.0) taudirac[ia].y -= 1.0; - if(taudirac[ia].z>=1.0) taudirac[ia].z -= 1.0; - - if(taudirac[ia].x<0 || taudirac[ia].y<0 - || taudirac[ia].z<0 || - taudirac[ia].x>=1.0 || - taudirac[ia].y>=1.0 || - taudirac[ia].z>=1.0) - { - cout << " ion: "<< ia << endl; - cout << "d=" << taudirac[ia].x << " " << - taudirac[ia].y << " " << taudirac[ia].z << endl; - WARNING_QUIT("md::moveatoms","the movement of atom is larger than the length of cell."); - } - - cartNoWrap[ia] = taudirac[ia] * ionlatvec*ucell.lat0; + Stress_PW ss; + ss.cal_stress(stress_pw); } return; } -void MD_func::printpos(string file,int iter) +void MD_func::printpos(const string& file, const int& iter, const int& recordFreq, const UnitCell_pseudo& unit_in) { //intend to output the positions of atoms to ordered file bool pass; pass = 0; - if (dumpmdfreq==1||iter==1||( dumpmdfreq > 1&& iter%dumpmdfreq==0 ) ) + if (recordFreq==1||iter==1||( recordFreq > 1&& iter%recordFreq==0 ) ) pass =1; if (!pass) return; @@ -587,26 +321,68 @@ void MD_func::printpos(string file,int iter) string file2=file+".cif"; //xiaohui add 'OUT_LEVEL', 2015-09-16 - if(OUT_LEVEL == "i"||OUT_LEVEL == "ie") ucell.print_tau(); - if(OUT_LEVEL == "i"||OUT_LEVEL == "ie") ucell.print_cell_xyz(file1); - ucell.print_cell_cif(file2); + if(OUT_LEVEL == "i"||OUT_LEVEL == "ie") unit_in.print_tau(); + if(OUT_LEVEL == "i"||OUT_LEVEL == "ie") unit_in.print_cell_xyz(file1); + unit_in.print_cell_cif(file2); stringstream ss; ss << global_out_dir << "STRU_MD"; //zhengdy modify 2015-05-06, outputfile "STRU_Restart" - ucell.print_stru_file(ss.str(),2); + unit_in.print_stru_file(ss.str(),2); return; } //rescale velocities to target temperature. -void MD_func::scalevel() +void MD_func::scalevel( + const int& numIon, + const int& nfrozen, + const double& temperature, + Vector3* vel, + const double* allmass +) { - double ke=GetAtomKE(); + double ke=GetAtomKE(numIon, vel, allmass); if(ke>1e-9) - for(int i=0;iconst* force){ + //cout<<"enter in MAXVALF"<* vel, int& step_rst); + void mdRestartOut(const int& step, const int& recordFreq, const int& numIon, Vector3* vel); + double GetAtomKE(const int& numIon, const Vector3const* vel, const double const* allmass); + void InitVelocity( + const int& numIon, + const double& temperature, + const double& fundamentalTime, + const double const* allmass, + Vector3* vel); +// void ReadNewTemp(int step); + string intTurnTostring(long int iter,string path); + int getMassMbl(const UnitCell_pseudo &unit_in, double* allmass, Vector3* ionmbl); + void callInteraction_LCAO(const int& numIon, Vector3* force, matrix& stress_lcao); + void callInteraction_PW(const int& numIon, Vector3* force, matrix& stress_pw); + void printpos(const string& file, const int& iter, const int& recordFreq, const UnitCell_pseudo& unit_in); + void scalevel( + const int& numIon, + const int& nfrozen, + const double& temperature, + Vector3* vel, + const double* allmass); + double MAXVALF(const int numIon, const Vector3const* force); + double Conserved(const double KE, const double PE, const int number); }; #endif \ No newline at end of file diff --git a/ABACUS.develop/source/src_pw/MD_parameters.h b/ABACUS.develop/source/src_pw/MD_parameters.h index 73fe75ff50..d985329b45 100644 --- a/ABACUS.develop/source/src_pw/MD_parameters.h +++ b/ABACUS.develop/source/src_pw/MD_parameters.h @@ -3,25 +3,43 @@ class MD_parameters { - MD_parameters(){}; +public: + MD_parameters() + { + mdtype=1; + NVT_tau=0; + NVT_control=1; + dt=1; + Qmass=1; + tfirst=0; //kelvin + tlast=-1; + recordFreq=1; + mdoutputpath="mdoutput"; + rstMD=0; + fixTemperature=1; + ediff=1e-4; + ediffg=1e-3; + MNHC=4; + }; ~MD_parameters(){}; - private: int rstMD; // 1 : restart MD, vel.restart and ion.restart files will be read // 0 : not restart from ion and vel files int mdtype; // 1: NVT:Nose Hoover, 2:NVT:velocity scaling 3: NPT, 0: NVE double Qmass; // Inertia of extended system variable double dt ; // Time increment (hbar/E_hartree) - double temperature; //Temperature (in Hartree, 1 Hartree ~ 3E5 K) - int ntype; // - int dumpmdfreq; // The period to dump MD information for monitoring and restarting MD + double tfirst; //Temperature (in Hartree, 1 Hartree ~ 3E5 K) + double tlast; + int recordFreq; // The period to dump MD information for monitoring and restarting MD int NVT_control; double NVT_tau; int MNHC; string mdoutputpath;// output directory of md files: .ion .vel double ediff; //parameter for constrain double ediffg; //parameter for constrain + int fixTemperature; }; + #endif \ No newline at end of file diff --git a/ABACUS.develop/source/src_pw/MD_run.cpp b/ABACUS.develop/source/src_pw/MD_run.cpp deleted file mode 100644 index e40142cd43..0000000000 --- a/ABACUS.develop/source/src_pw/MD_run.cpp +++ /dev/null @@ -1,540 +0,0 @@ -#include "MD_run.h" - -//define in MD_run.h -//class MD_run - - -void MD_run::runnvt(int step1){ -//------------------------------------------------------------------------------ -// DESCRIPTION: -// Molecular dynamics calculation with fixed Volume and slight fluctuated temperature -// Using thermostat : 1, Nose-Hoover Chains; 2, Langevin; 3, Anderson -// Normal Nose-Hoover thermostat method is retained for test. -//------------------------------------------------------------------------------ - - TITLE("MD_run","runnvt"); - timer::tick("MD_run","runnvt",'C'); - step=step1+step_rst; - //the real MD step - if (!MY_RANK)out<<"step: " << step < fracStep; - for(int ii=0;iimaxStep) - { - maxStep = pow(vel[ii].x,2)+pow(vel[ii].y,2)+pow(vel[ii].z,2); - } - Mathzone::Cartesian_to_Direct(vel[ii].x*dt/ucell.lat0,vel[ii].y*dt/ucell.lat0,vel[ii].z*dt/ucell.lat0, - ionlatvec.e11,ionlatvec.e12,ionlatvec.e13, - ionlatvec.e21,ionlatvec.e22,ionlatvec.e23, - ionlatvec.e31,ionlatvec.e32,ionlatvec.e33, - fracStep.x,fracStep.y,fracStep.z); - - taudirac[ii] = taudirac[ii] + fracStep; - } - - //save the atom position change to DFT module - moveatoms(step); - string t("md_pos_"); - t=intTurnTostring(step,t); - connection2(); - printpos(t,step); - maxStep = sqrt(maxStep)*dt; - - if (!MY_RANK){ - out<maxStep) - { - maxStep = pow(vel[i].x,2.0)+pow(vel[i].y,2.0)+pow(vel[i].z,2.0); - } - Mathzone::Cartesian_to_Direct(vel[i].x*dt/ucell.lat0,vel[i].y*dt/ucell.lat0,vel[i].z*dt/ucell.lat0, - ionlatvec.e11,ionlatvec.e12,ionlatvec.e13, - ionlatvec.e21,ionlatvec.e22,ionlatvec.e23, - ionlatvec.e31,ionlatvec.e32,ionlatvec.e33, - fracStep.x,fracStep.y,fracStep.z); - taudirac[i] = taudirac[i] + fracStep; - } - moveatoms(step); - string t("md_pos_"); - t=intTurnTostring(step,t); - connection2(); - printpos(t,step); - maxStep = sqrt(maxStep)*dt; - - - // calculate the conserved quantity during MD - hamiltonian = Conserved(twiceKE/2, mdenergy); - - cout<< setprecision (9)<maxStep) - { - maxStep = pow(vel[i].x,2.0)+pow(vel[i].y,2.0)+pow(vel[i].z,2.0); - } - Mathzone::Cartesian_to_Direct(vel[i].x*dt/ucell.lat0,vel[i].y*dt/ucell.lat0,vel[i].z*dt/ucell.lat0, - ionlatvec.e11,ionlatvec.e12,ionlatvec.e13, - ionlatvec.e21,ionlatvec.e22,ionlatvec.e23, - ionlatvec.e31,ionlatvec.e32,ionlatvec.e33, - fracStep.x,fracStep.y,fracStep.z); - taudirac[i] = taudirac[i] + fracStep; - } - - moveatoms(step); - string t("md_pos_"); - t=intTurnTostring(step,t); - connection2(); - printpos(t,step); - maxStep = sqrt(maxStep)*dt; - - hamiltonian = Conserved(twiceKE/2, mdenergy); - - - - - // Output the message to the screen. - oldEtot=mdenergy; - - cout<<"(NVE): this step finished."<[1]; + NHCeta = new Vector3[1]; + NHCpeta = new Vector3[1]; +} + +MD_thermo::~MD_thermo() +{ + delete[] G; + delete[] NHCeta; + delete[] NHCpeta; +} + +void MD_thermo::init_NHC( const int &MNHC_in, + const double &Qmass_in, + const double &NVT_tau_in, + const double &dt_in, const int &NVT_control, ofstream &ofs, - const int &numIon + const int &numIon, + const double &temperature, + const Vector3* vel, + const double* allmass ) { - this->MNHC = MNHC_in; + this->MNHC_ = MNHC_in; + this->Qmass_ = Qmass_in; + this->NVT_tau_ = NVT_tau_in; + this->dt_ = dt_in; + this->numIon_ = numIon; unsigned long init[4]={0x123, 0x234, 0x345, 0x456}, length=4; init_by_array(init, length); ofs<<" ...............Nose-Hoover Chain parameter initialization............... " << endl; ofs<<" Temperature = "<< temperature << endl; ofs<<" Temperature2 = "<< temperature/K_BOLTZMAN_AU << endl; - ofs<<" NHC frequency = "<< 1.0/NVT_tau << endl; - ofs<<" NHC chain = "<< MNHC << endl; - ofs<<" Qmass = "<< Qmass << endl; + ofs<<" NHC frequency = "<< 1.0/NVT_tau_ << endl; + ofs<<" NHC chain = "<< MNHC_ << endl; + ofs<<" Qmass = "<< Qmass_ << endl; ofs<<" ............................................................... " << endl; w[0]=0.7845136105; w[6]=0.7845136105; @@ -27,44 +51,44 @@ MD_thermo::init_NHC( // for(int i=0;i[MNHC*numIon]; + G=new Vector3[MNHC_*numIon_]; delete[] NHCeta; - NHCeta=new Vector3[MNHC*numIon]; + NHCeta=new Vector3[MNHC_*numIon_]; delete[] NHCpeta; - NHCpeta=new Vector3[MNHC*numIon]; + NHCpeta=new Vector3[MNHC_*numIon_]; - for(int j=0;j=1;j--) + for(int j=MNHC_-1;j>=1;j--) { - for(int k=0;k* vel, + const double* allmass) { - if(control == 1) NHCIntegrator(); - else if(control == 2) LGVIntegrator(); - else if(control == 3) ADSIntegrator(); + if(control == 1) NHCIntegrator(temperature, vel, allmass); + else if(control == 2) LGVIntegrator(temperature, vel, allmass); + else if(control == 3) ADSIntegrator(temperature, vel, allmass); else WARNING_QUIT("MD_thermo:Integrator", "please choose available reservoir!!!"); return; } -void MD_thermo::LGVIntegrator() +void MD_thermo::LGVIntegrator( + const double &temperature, + Vector3* vel, + const double* allmass +) { //--------------------------------------------------------------------------- // DESCRIPTION: @@ -289,11 +311,11 @@ void MD_thermo::LGVIntegrator() //-------------------------------------------------------------------- double randomx,randomy,randomz; double tempV; - double c1k = exp(-1/NVT_tau * dt); + double c1k = exp(-1/NVT_tau_ * dt_); //c1k=e^(-gamma*dt) double c2k=sqrt(1.0-c1k*c1k); - for(int iatom=0;iatom* vel, + const double* allmass +) { //--------------------------------------------------------------------------- // DESCRIPTION: @@ -326,13 +352,13 @@ void MD_thermo::ADSIntegrator() double rany; double ranz; - double nu = 1/ NVT_tau; + double nu = 1/ NVT_tau_; - for(int iatom=0;iatom* vel, + const double* allmass +){ //--------------------------------------------------------------------------- // DESCRIPTION: // This function propagates the Nose-Hoover Chain @@ -368,85 +398,212 @@ void MD_thermo::NHCIntegrator(){ // Q : NHC mass //-------------------------------------------------------------------- - for(int i=0;i=0;j--) + for(int j=MNHC_-2;j>=0;j--) { - for(int k=0;k=0;j--) + for(int j=MNHC_-1;j>=0;j--) { - for(int k=0;k 1&& step%recordFreq==0 ) ) + pass =1; + if (!pass) return; + + if(!MY_RANK){ + stringstream ssc; + ssc << global_out_dir << "Restart_md.dat"; + ofstream file(ssc.str().c_str(), ios::app); + file<<'\n'; + file<<"MD_THERMOSTAT"< +void MD_thermo::NHC_restart() +{ + int error=0; + double *nhcg=new double[numIon_*3*MNHC_]; + double *nhcp=new double[numIon_*3*MNHC_]; + double *nhce=new double[numIon_*3*MNHC_]; + if (!MY_RANK) + { + stringstream ssc; + ssc << global_readin_dir << "Restart_md.dat"; + ifstream file(ssc.str().c_str()); + + char word[80]; + int mnhc; + while(file.good())//search and read MNHC + { + file>>word; + if(std::strcmp("MNHC:",word)==0) + { + file>>mnhc; + break; + } + else + { + file.ignore(150, '\n'); + } + } + + if(mnhc!=MNHC_) + { + cout<<"please ensure whether 'Restart_md.dat' right!"<>nhcg[i]; + } + file.get(); + file.ignore(8, '\n');//read eta + for(int i = 0;i>nhce[i]; + } + file.get(); + file.ignore(9, '\n');//read peta + for(int i = 0;i>nhcp[i]; + } + file.close(); + } + + } +#ifdef __MPI + MPI_Bcast(&error,1,MPI_INT,0,MPI_COMM_WORLD); +#endif + if(error) + { + delete[] nhcg; + delete[] nhcp; + delete[] nhce; + exit(0); + } +#ifdef __MPI + MPI_Bcast(nhcg,numIon_*3*MNHC_,MPI_DOUBLE,0,MPI_COMM_WORLD); + MPI_Bcast(nhcp,numIon_*3*MNHC_,MPI_DOUBLE,0,MPI_COMM_WORLD); + MPI_Bcast(nhce,numIon_*3*MNHC_,MPI_DOUBLE,0,MPI_COMM_WORLD); +#endif + + for(int i=0;i* vel, + const double* allmass + ); void init_NHC( const int &MNHC_in, + const double &Qmass_in, + const double &NVT_tau_in, + const double &dt_in, const int &NVT_control, ofstream &ofs, - const int &numIon + const int &numIon, + const double &temperature, + const Vector3* vel, + const double* allmass ); double NHChamiltonian( const double &KE, const double &PE, - const int &numIon, const double &temperature, - const int &nfrozen ); + const int &nfrozen + ); + + void NHC_info_out(const int& step, const int& recordFreq, const int& numIon); + void NHC_restart(); private: - void ADSIntegrator(); - void LGVIntegrator(); - void NHCIntegrator(); + void ADSIntegrator( + const double &temperature, + Vector3* vel, + const double* allmass + ); + void LGVIntegrator( + const double &temperature, + Vector3* vel, + const double* allmass + ); + void NHCIntegrator( + const double &temperature, + Vector3* vel, + const double* allmass + ); + double gaussrand(); @@ -35,7 +63,7 @@ class MD_thermo double genrand_real1(void); double genrand_real2(void); double genrand_real3(void); - double genrand_res53(void) ; + double genrand_res53(void); //NVT thermostat parameters const static int N_mt19937=624; @@ -47,19 +75,24 @@ class MD_thermo int mti=625; /* mti==N+1 means mt[N] is not initialized */ long double gamma; //langevin friction coefficient long double nu; //Andersen collision frequency - long long double c1k; //parameter in Langevin + long double c1k; //parameter in Langevin double c2k; //parameter in Langevin const static int nsy=7; //parameter in NHC, constant, no need to modification - long double w[nsy]; //parameters in NHC - long double delta[nsy]; //parameters in NHC + double w[nsy]; //parameters in NHC + double delta[nsy]; //parameters in NHC //input parameters - int MNHC; - int Qmass; + int MNHC_; + double Qmass_; + double NVT_tau_; + double dt_; + int numIon_; //need to be allocated Vector3 *G; //parameter in NHC Vector3 *NHCeta; //NHC position Vector3 *NHCpeta; //NHC momentum -}; \ No newline at end of file +}; + +#endif \ No newline at end of file diff --git a/ABACUS.develop/source/src_pw/md.cpp b/ABACUS.develop/source/src_pw/md.cpp deleted file mode 100644 index be99fd8763..0000000000 --- a/ABACUS.develop/source/src_pw/md.cpp +++ /dev/null @@ -1,1211 +0,0 @@ -//Description:this module is the base of MD simulation -#include -#include -#include -#include -#include -#include -#include"md.h" -#include"../input.h" -#include"../src_lcao/LOOP_ions.h" -#include "../src_global/sltk_atom_arrange.h" //2015-10-01, xiaohui - -md::md(int n) -{ - xLogS=0; // thermostat's position - vLogS=0 ;// thermostat's speed - tauthermo = 0; // The thermostat fluctuation period, for Al fcc at 300K ~ 1000fs - taubaro = 0 ; // The barostat fluctuation period, for Al fcc at 300K ~ 500 fs - Qmass = -1; // Inertia of extended system variable - dt = -1; // Time increment (hbar/E_hartree) - temperature= -1; //Temperature (in Hartree, 1 Hartree ~ 3E5 K) - doMSD = 1; // compute the mean square displacement. - doMSDAtom = 1; // compute the mean square displacement for each atom. - msdstartTime = 1; //beyond this time, msd is going to be computed - diffuCoeff = 0; - nResn=3; // Coarseness of Trotter factorization of Nose-Hoover thermostat - nYosh=3; // Order of thermostat scheme corresponding with "intCoeff" - outputstressperiod = 1 ;// The period to output stress - dumpmdfreq = 1 ; // The period to dump MD information for monitoring and restarting MD - fixTemperature = 1; // The period to read in new temperature during MD run. - rstMD = 0 ;// 1 : restart MD, vel.restart and ion.restart files will be read - // 0 : not restart from ion and vel files - // -n: restart from vel.n and ion.n in directory - // "md_output_path" - - startStep=0 ;// the first step number of MD - velRescale = 0 ;// whether to rescale velocities at the first step - mdoutputpath="mdDataOut"; - step_rst=0; - numIon=ucell.nat; - ntype=ucell.ntype; -}; - -void md::md_allocate() -{ - na=new int[ntype]; - if (!MY_RANK) - { - stringstream ssc; - ssc << global_out_dir << "MD_OUT"; - out.open(ssc.str().c_str()); - } - for(int i=0;i[numIon]; - cartNoWrap=new Vector3[numIon]; - taudirac=new Vector3[numIon]; - allmass=new double[numIon]; - ionmbl=new Vector3[numIon]; - force=new Vector3[numIon]; - return; -} - -const double md::fundamentalTime = 2.418884326505e-17; - -void md::initMD(void) -{ - - mdtype=INPUT.md_mdtype; - - mdenergy=en.etot/2; - - Qmass=INPUT.md_qmass/6.02/9.109*1e5; - dt=INPUT.md_dt/fundamentalTime/1e15; - temperature=INPUT.md_tfirst/3.1577464e5; - rstMD=INPUT.md_rstmd; - - nResn=INPUT.md_nresn; - nYosh=INPUT.md_nyosh; - dumpmdfreq=INPUT.md_dumpmdfred; - fixTemperature=INPUT.md_fixtemperature; - ediff=INPUT.md_ediff; - ediffg=INPUT.md_ediffg; - doMSD=INPUT.md_domsd; - doMSDAtom=INPUT.md_domsdatom; - mdoutputpath=INPUT.md_mdoutpath; - msdstartTime=INPUT.md_msdstartTime; - - if(rstMD==0) - { - connection0(); - connection1(); - //A fresh new MD: Do not restart MD - InitVelocity() ; - // Initialize thermostat, and barostat - xLogS = 0.0 ; // position of thermostat - vLogS = 0.0; // velocity of thermostat - } - else if( rstMD>0 ) - { - connection0(); - connection1(); - InitVelocity() ; - if(!RestartMD()){ - cout<<"error in restart MD!"<>xLogS; - file.get(); file.ignore(7, '\n'); - file>>vLogS; - file.get(); file.ignore(23, '\n'); - for(i = 0;i>vell[i]; - } - /*file.get(); file.ignore(17, '\n'); - for(i=0;i>cart[i]; - } - file.get(); file.ignore(13, '\n'); - for(i=0;i>dira[i]; - }*/ - file.get(); - file.ignore(6, '\n'); - file>>step_rst; - file.close(); - } - -//2015-09-05, xiaohui -#ifdef __MPI - MPI_Bcast(&xLogS,1,MPI_DOUBLE,0,MPI_COMM_WORLD); - MPI_Bcast(&vLogS,1,MPI_DOUBLE,0,MPI_COMM_WORLD); - MPI_Bcast(&step_rst,1,MPI_INT,0,MPI_COMM_WORLD); - MPI_Bcast(vell,numIon*3,MPI_DOUBLE,0,MPI_COMM_WORLD); - // MPI_Bcast(cart,numIon*3,MPI_DOUBLE,0,MPI_COMM_WORLD); - // MPI_Bcast(dira,numIon*3,MPI_DOUBLE,0,MPI_COMM_WORLD); -#endif - - for(i=0;i echo_md_restart.dat, for debug purpose. "< 1&& step%dumpmdfreq==0 ) ) - pass =1; - if (!pass) return; - - int i; - if(!MY_RANK) - { - stringstream ssc; - ssc << global_out_dir << "Restart_md.dat"; - ofstream file(ssc.str().c_str()); - file<<"MD_RESTART"<> EXTERNAL VARIABLES <> INTERIOR VARIABLES <> INITIALIZATION <> FUNCTION BODY <=0) i1=i0; else i1=i0+m; - i0=a*(j%q)-r*((j-j%q)/q); - if(j0>=0) j1=j0; else j1=j0+m; - for(M=0;M<3*numIon;) - { - i0=a*(i1%q)-r*((i1-i1%q)/q); - if(i0>=0) i2=i0; - else i2=i0+m; - u=((double)i1)/((double)m); //first ramdon number - i1=i2; - j0=a*(j1%q)-r*((j1-j1%q)/q); - if(j0>=0) j2=j0; - else j2=j0+m; - v=((double)j1)/((double)m); //second ramdon number - j1=j2; - x=tan(PI*(u-0.5)); - y=1.6*v/(PI*(x*x+1.0)); - if(y<=(1.0/sqrt(2.0*PI)*exp(-0.5*x*x))) - { - if(M> EXTERNAL VARIABLES <> LOCAL VARIABLES << !! - int i, ii, it,ion,nfrozen; - double vel1, vel2, mass, KE ; //KE: to store kinetic energy - - TITLE("md","InitVelocity"); - - // note from mohan 2013-03 - // get the random wave functions from processor 1!! - // otherwise the velocity on each node will be different! - // then the geometry will be different at each MD step - // the results are totally wrong. - srand( (unsigned)time( NULL ) ); - // Assign random numbers to velocities - for(i = 1; i> LOCAL VARIABLES << !! - int ii,it, id,j,ion; - Vector3 avgvel; - double mass,totMass; - - //!! >> FUNCTION << !! - - avgvel.x = 0; - avgvel.y=0; - avgvel.z=0; - totMass = 0; - - // sum up the total momentum of all the atoms - // in the system. (Px,Py,Pz) =\sum m_{i}*(vx,vy,vz)_{i} - for(ion=0;ion>> FUNCTION BODY << -// <...> denotes the averaging over all the atoms -// -// For solids, MSD saturates to a finte value, for liquids, -// MSD grows linearly with time. -// -// Also compute the diffusion coefficient D: -// D = MSD/(6*t) -//---------------------------------------------------------------------------- - - //! >> LOCAL VARIABLES << ! - Matrix3 box; - int it,ii,jj,ion,i; - double timePassed; - double *tmp; - tmp =new double[ntype]; - Vector3 diff; - // INITIALIZATION - // box.e11 =ionlatvec.e11; - // box.e12 =ionlatvec.e12; -// box.e13=ionlatvec.e13; -// box.e21 =ionlatvec.e21; -// box.e22 =ionlatvec.e22; -// box.e23 =ionlatvec.e23; -// box.e31 =ionlatvec.e31; -// box.e32 =ionlatvec.e32; -// box.e33 =ionlatvec.e33; - box=ionlatvec; - - - - //! >> FUNCTION << ! - if(msdstartTime>step-step_rst)return; - if (doMSD ==1) { - - if (step-step_rst == msdstartTime) { - msdcoords0=new Vector3[numIon]; - msdcoordst=new Vector3[numIon]; - if(rstMD==1){ - double *msd0=new double[numIon*3]; - double *msdt=new double[numIon*3]; - if (!MY_RANK){ - stringstream ssc; - ssc << global_out_dir << "Restart_msd.dat"; - ifstream file(ssc.str().c_str()); - if(!file){ - cout<<"please ensure whether 'Restart_msd.dat' exists"<>msd0[i]; - } - for(i=0;i>msdt[i]; - } - } - file.close(); - } -//2015-09-05, xiaohui -#ifdef __MPI - MPI_Bcast(msd0,numIon*3,MPI_DOUBLE,0,MPI_COMM_WORLD); - MPI_Bcast(msdt,numIon*3,MPI_DOUBLE,0,MPI_COMM_WORLD); -#endif - for(i=0;i msdstartTime){ - for(ion=0;ion msd_startTime) - if(step==NSTEP){ - if(msdcoords0!=NULL)delete []msdcoords0; - if(msdcoordst!=NULL)delete []msdcoordst; - } - } // doMSD - return; - } - - - void md::OutputIonVelocityAndStats(int iter){ -//--------------------------------------------------------------------------- -// DESCRIPTION: -// Output the -// (1) ion's velocity -// (2) thermostat's xLogS, and vLogs (for NVT, NPT) -// (3) barostat's vbox (box's velocity) (NPT only) -// for restart purpose -//--------------------------------------------------------------------------- -// REVISION LOG: -// Dec/29/2008: Created by Chen Huang -//---------------------------------------------------------------------------- - - // iter, mdtype //number of ions, iteration number, NVT/NPT - -//2015/4/30:change to output msd data for restart. - int i,j; - - bool pass; - pass = 0; - - - if (dumpmdfreq==1||iter==1||( dumpmdfreq > 1&& iter%dumpmdfreq==0 ) ) - pass =1; - if (!pass) return; - - if (msdstartTime>iter)return; - if (!MY_RANK){ - stringstream ssc; - ssc << global_out_dir << "Restart_msd.dat"; - ofstream vfile(ssc.str().c_str()); - -/* vfile<<"MD STEP= "<> FUNCTION << ! - pass = 0; - // if(rankGlobal!=0) return; - if(dumpmdfreq==1||iter==1||( dumpmdfreq > 1&&(iter%dumpmdfreq)==0 ) ) - pass = 1; - if(!pass)return; - // cout<<"test the function OutputMDGeom"< 0 ){ - - // Change the temperature every 'fixTemperature' steps. - if( (step!=1)&&(step%fixTemperature == 1) ){ - - // Read in new temperature from file. - ifstream file; - file.open("ChangeTemp.dat"); - if (!file){ - cout<<"ERROR IN OPENING ChangeTemp.dat, CODE STOP!"<> intemp; - sstep+=fixTemperature; - } - file.close(); - - // Renew information. - intemp = intemp * K_BOLTZMAN_AU; - if ( fabs(intemp-temperature) >1e-6 ) { - cout <<"(ReadNewTemp): Read in new temp:"<< intemp/K_BOLTZMAN_AU - <<" previous temp:"<< temperature/K_BOLTZMAN_AU<99999){ - k=6; - i[5]=iter%10; - iter=iter/10; - i[4]=iter%10; - iter=iter/10; - i[3]=iter%10; - iter=iter/10; - i[2]=iter%10; - iter=iter/10; - i[1]=iter%10; - iter=iter/10; - i[0]=iter%10; - } - else if(iter>9999){ - k=5; - i[4]=iter%10; - iter=iter/10; - i[3]=iter%10; - iter=iter/10; - i[2]=iter%10; - iter=iter/10; - i[1]=iter%10; - iter=iter/10; - i[0]=iter%10; - } - else if(iter>999){ - k=4; - i[3]=iter%10; - iter=iter/10; - i[2]=iter%10; - iter=iter/10; - i[1]=iter%10; - iter=iter/10; - i[0]=iter%10; - } - else if(iter>99){ - k=3; - i[2]=iter%10; - iter=iter/10; - i[1]=iter%10; - iter=iter/10; - i[0]=iter%10; - } - else if(iter>9){ - k=2; - i[1]=iter%10; - iter=iter/10; - i[0]=iter%10; - } - else if(iter>0){ - k=1; - i[0]=iter; - } - for(int j=0;j avgdc; - double mass,totMass; - - //!! >> FUNCTION << !! - -// 2015/9/18 no move of center of mass -/* - avgdc.x = 0; - avgdc.y=0; - avgdc.z=0; - totMass = 0; - - // sum up the total momentum of all the atoms - // in the system. (Px,Py,Pz) =\sum m_{i}*(vx,vy,vz)_{i} - for(ion=0;ion=1.0) taudirac[ia].x -= 1.0; - if(taudirac[ia].y>=1.0) taudirac[ia].y -= 1.0; - if(taudirac[ia].z>=1.0) taudirac[ia].z -= 1.0; -/* - if(taudirac[ia].x<0){ - taudirac[ia].x *= -1.0; - vel[ia].x *=-1.0; - } - if(taudirac[ia].y<0) { - taudirac[ia].y *= -1.0; - vel[ia].y *=-1.0; - } - if(taudirac[ia].z<0) { - taudirac[ia].z *= -1.0; - vel[ia].z *=-1.0; - } - if(taudirac[ia].x>=1.0){ - taudirac[ia].x = 2.0-taudirac[ia].x; - vel[ia].x *=-1.0; - } - if(taudirac[ia].y>=1.0){ - taudirac[ia].y = 2.0-taudirac[ia].y; - vel[ia].y *=-1.0; - } - if(taudirac[ia].z>=1.0){ - taudirac[ia].z = 2.0-taudirac[ia].z; - vel[ia].z *=-1.0; - } -*/ - if(taudirac[ia].x<0 || taudirac[ia].y<0 - || taudirac[ia].z<0 || - taudirac[ia].x>=1.0 || - taudirac[ia].y>=1.0 || - taudirac[ia].z>=1.0) - { - cout << " ion: "<< ia << endl; - cout << "d=" << taudirac[ia].x << " " << - taudirac[ia].y << " " << taudirac[ia].z << endl; - WARNING_QUIT("md::moveatoms","the movement of atom is larger than the length of cell."); - } - - cartNoWrap[ia] = taudirac[ia] * ionlatvec*ucell.lat0; - } - return; -} -void md::printpos(string file,int iter){ -//intend to output the positions of atoms to ordered file - bool pass; - pass = 0; - - - if (dumpmdfreq==1||iter==1||( dumpmdfreq > 1&& iter%dumpmdfreq==0 ) ) - pass =1; - if (!pass) return; - - string file1=file+".xyz"; - string file2=file+".cif"; - - //xiaohui add 'OUT_LEVEL', 2015-09-16 - if(OUT_LEVEL == "i"||OUT_LEVEL == "ie") ucell.print_tau(); - if(OUT_LEVEL == "i"||OUT_LEVEL == "ie") ucell.print_cell_xyz(file1); - ucell.print_cell_cif(file2); - stringstream ss; - - ss << global_out_dir << "STRU_MD"; - - //zhengdy modify 2015-05-06, outputfile "STRU_Restart" - ucell.print_stru_file(ss.str(),2); - - return; -} -void md::md_release(){ - - if(force!=NULL)delete []force; - if(ionmbl!=NULL)delete []ionmbl; - if(cartNoWrap!=NULL)delete []cartNoWrap; - if(vel!=NULL)delete []vel; - if(taudirac!=NULL)delete []taudirac; - if(allmass!=NULL)delete []allmass; - - return; -} -void md::scalevel(){ - int i; - double ke=GetAtomKE(); - if(ke>1e-9) - for(i=0;i((double)k*c/(double)100))rdf[k]=rdf[k]+1; - } - } - } - return; -} -void md::printRDF(int step){ - int i; - ofstream file; -// if(step==1){ -// file.open("RDFnow.dat"); - // file.close(); - // } - string it="RDF"; - if(fixTemperature!=0) - if(step/fixTemperature!=0) intTurnTostring(step/fixTemperature,it); - it+=".dat"; - if(step%dumpmdfreq==1){ - file.open(it.c_str()); - file<0&&cartNoWrap[i].x+11.342<0) - for(j=0;j((double)k/5.29+0.0945))rdf[k]=rdf[k]+1; - } - } - } - return; -}*/ diff --git a/ABACUS.develop/source/src_pw/md.h b/ABACUS.develop/source/src_pw/md.h deleted file mode 100644 index 3aee8f41d5..0000000000 --- a/ABACUS.develop/source/src_pw/md.h +++ /dev/null @@ -1,111 +0,0 @@ -#ifndef MD_H -#define MD_H - -#include -#include -#include -#include -#include -#include -#include"tools.h" -#include"global.h" -#include"../src_lcao/FORCE_STRESS.h" -#include"unitcell_pseudo.h" - -using namespace std; - -//const double fundamentalTime = 2.418884326505e-17; - -//------------------------------------------------------------------- -// mohan reconstruction note: 2021-02-07 -// 1) explain every variable and every function -// 2) if too many, divide the class into more files -// 3) leave a space between different functions -// 4) write the comments above the variables or functions -//------------------------------------------------------------------- - -class md -{ - public: - - md(int n=1); - - void md_allocate(); - void initMD(); - bool RestartMD(); - void mstout(int step); - void RemoveMovementOfCenterOfMass(); - double GetAtomKE(); - void MakeIntCoeff(); - void InitVelocity(); - void MonitorMeanSquareDisplacement(int step); - void OutputIonVelocityAndStats(int iter); - void OutputMDHeader(); - void OutputMDGeom(int iter); - void ReadNewTemp(int step); - string intTurnTostring(int iter,string path); - void connection0(); - void connection1(); - void connection2(); - void callforce(); - void moveatoms(int step); - void printpos(string file,int iter); - void md_release(); - void scalevel(); - void RDF(); - void printRDF(int step); - void PDF(int step); - - // variables: - - int mdtype; // 1: NVT:Nose Hoover, 2:NVT:Nose Hoover add velocity scaling 3: NPT, 0: NVE - double xLogS; // thermostat's position - double vLogS;// thermostat's speed - Vector3 *vel;// velocity of each atom, unit is a.u. - Matrix3 vBoxG; // barostat's velocity - Matrix3 ionlatvec; - double tauthermo; // The thermostat fluctuation period, for Al fcc at 300K ~ 1000fs - double taubaro; // The barostat fluctuation period, for Al fcc at 300K ~ 500 fs - double Qmass; // Inertia of extended system variable - double dt ; // Time increment (hbar/E_hartree) - double temperature; //Temperature (in Hartree, 1 Hartree ~ 3E5 K) - bool doMSD; // compute the mean square displacement. - bool doMSDAtom; // compute the mean square displacement for each atom. - double msdstartTime; //beyond this time, msd is going to be computed - double *msd ; - double diffuCoeff ; - int numIon; - int ntype; - int* na; - int nfrozen; - double *allmass; - Vector3 *force; - Vector3 *ionmbl; - Vector3 *taudirac; //dirac coord of atoms - Vector3 *cartNoWrap; //cartensian coord of atoms, *not* wrapped - Vector3 *msdcoords0; - Vector3 *msdcoordst; - int nResn; // Coarseness of Trotter factorization of Nose-Hoover thermostat - int nYosh; // Order of thermostat scheme corresponding with "intCoeff" - double *intCoeff; - int outputstressperiod;// The period to output stress - int dumpmdfreq; // The period to dump MD information for monitoring and restarting MD - int fixTemperature; // The period to read in new temperature during MD run. - string mdoutputpath; // output directory of md files: .ion .vel - int rstMD;// 1 : restart MD, vel.restart and ion.restart files will be read - // 0 : not restart from ion and vel files - - double ediff; //parameter for constrain - double ediffg; //parameter for constrain - int startStep;// the first step number of MD - bool velRescale;// whether to rescale velocities at the first step - ofstream out; - double mdenergy; - const static double fundamentalTime; - double rdf[100]; - int step_rst; - - matrix stress_lcao; -}; - -#endif diff --git a/ABACUS.develop/source/src_pw/mdNVE.cpp b/ABACUS.develop/source/src_pw/mdNVE.cpp deleted file mode 100644 index ffb3a199f5..0000000000 --- a/ABACUS.develop/source/src_pw/mdNVE.cpp +++ /dev/null @@ -1,436 +0,0 @@ -#include"mdNVE.h" - -/* -using namespace std; -class mdNVE:public md{ -public: - mdNVE(int n=1):md(1){}; - void runNVE(); - void RescaleVelocity(double KE,double newKE); - double Conserved(double KE, double PE); - double MAXVALF(); -private: - //>> INTERNAL VARIABLES < velocity; // Velocity of ions (atomic units) - Vector3 fracStep; // Step (due to velocity) in fractional coordinates - double mass; // atom mass, temperay var - double maxStep; // Largest movement by an ion - double hamiltonian,conservedE,maxForce; - double msd; // mean square displacement - double diffuCoeff; // diffusion coefficient - double newKE; - double twiceKE; // Kinetic energy x 2 - double oldEtot; // old energy - - //TYPE(stopwatch):: & // Timer objects - // watch, & - // watch2 - - //string parameterInfo; // Line containing values for Qmass, dt, temperature for output to header - - double tempNow; - -}; -*/ - -void mdNVE::runNVE(int step1){ -//------------------------------------------------------------------------------- -// -// REFERENCES: -// Martyna et. al., "Explicit reversible integrators for extended system -// dynamics," Mol. Phys. 87 (1996), 1117. -// Allen and Tildesley, "Computer Simulation of Liquids" (predictor-corrector) -// Frenkel and Smit, "Understanding Molecular Simulation". -// -//------------------------------------------------------------------------------ -// REVISION LOG: -// 04-17-2013: revised from NVT code. -// -//------------------------------------------------------------------------------ - - - - // Optimizer // A subroutine that is called to optimize the electron density relative to the ion positions - - - // rho // Electron density, realspace - // energy // Energy from electronic optimization - //Vector3 forces; // Total forces. - // First is ion number, second direction (1,2,3 for x,y,z) - - - - //>> INITIALIZATION <[numIon]; - //cartNoWrap=new Vector3[numIon]; - - - // Set up extra output to ion optimizer / MD header - cout<<"Time interval : "<< dt*fundamentalTime*1e15<< " (fs)"<> FUNCTION BODY <maxStep) - maxStep = pow(vel[i].x,2.0)+pow(vel[i].y,2.0)+pow(vel[i].z,2.0); - Mathzone::Cartesian_to_Direct(vel[i].x*dt/ucell.lat0,vel[i].y*dt/ucell.lat0,vel[i].z*dt/ucell.lat0, - ionlatvec.e11,ionlatvec.e12,ionlatvec.e13, - ionlatvec.e21,ionlatvec.e22,ionlatvec.e23, - ionlatvec.e31,ionlatvec.e32,ionlatvec.e33, - fracStep.x,fracStep.y,fracStep.z); -// fracStep = ionlatvec.Inverse()* vel[i]*dt/ucell.lat0; - taudirac[i] = taudirac[i] + fracStep; - } - // cout<<"dx: "<> INTERNAL VARIABLES <> INITIALIZATION <> FUNCTION BODY <> INITIALIZATION <> FUNCTION BODY <> INTERNAL VARIABLES < velocity; // Velocity of ions (atomic units) - Vector3 fracStep; // Step (due to velocity) in fractional coordinates - double mass; // atom mass, temperay var - double maxStep; // Largest movement by an ion - double hamiltonian,conservedE,maxForce; - double msd; // mean square displacement - double diffuCoeff; // diffusion coefficient - double newKE; - double twiceKE; // Kinetic energy x 2 - double oldEtot; // old energy - - //TYPE(stopwatch):: & // Timer objects - // watch, & - // watch2 - - //string parameterInfo; // Line containing values for Qmass, dt, temperature for output to header - - double tempNow; - -}; -#endif diff --git a/ABACUS.develop/source/src_pw/mdNVT.cpp b/ABACUS.develop/source/src_pw/mdNVT.cpp deleted file mode 100644 index 42878cbc9d..0000000000 --- a/ABACUS.develop/source/src_pw/mdNVT.cpp +++ /dev/null @@ -1,456 +0,0 @@ -#include "mdNVT.h" - -const double EXP=2.71828; -/* -using namespace std; -class mdnvt:public md{ -public: mdnvt(int n=1):md(1){}; - void runnvt(); - void NHIntegrator(); - double NHhamiltonian(double KE,double PE); - double MAXVALF(); -private: - int nfrozen;// ! Number of frozen atoms - int ii,k,it,ion;// - int i;// ! Counters to parse through the ion table. - int step;// ! step number we are on - //int numIon;// ! total number of atoms - int nStep;// ! Total number of steps - int errorFlag; - double mass; // atom mass, temperay var - double maxStep; // Largest movement by an ion - //double xLogS; // position of thermostat - //double vLogS; // vel of thermostat - double hamiltonian; // conserved energy - double maxForce; - //double msd; // mean square displacement - //double diffuCoeff; // diffusion coefficient - double twiceKE; // Kinetic energy x 2 - double oldEtot; // old energy -}; -*/ -void mdnvt::runnvt(int step1){ -//------------------------------------------------------------------------------ -// DESCRIPTION: -// This subroutine integrates motion for molecular dynamics using the -// Nose-Hoover thermostat coupled with a predictor-corrector integrator. -// REFERENCES: -// Martyna et. al., "Explicit reversible integrators for extended system -// dynamics," Mol. Phys. 87 (1996), 1117. -// Allen and Tildesley, "Computer Simulation of Liquids" (predictor-corrector) -// Frenkel and Smit, "Understanding Molecular Simulation". -//------------------------------------------------------------------------------ -//REVISION LOG: -// 10/20/2008 : Adapted from subroutines in IonOptimizers and symplectic -// algorithm from Martyna et. al. with help from Frenkel/Smit. -// -//------------------------------------------------------------------------------ -// Vector4 rho; // Electron density, realspace -// Vector energy; // Energy from electronic optimization - //Vector3 forces;// Total forces. Final index is 0 for total force, - // First is ion number, second direction (1,2,3 for x,y,z) - - - //REAL(KIND=DP), ALLOCATABLE, DIMENSION(:,:) :: vel // vel of ions (atomic units) - //double intCoeff[]; - //REAL(KIND=DP), DIMENSION(3) :: fracStep // Step (due to vel) in fractional coordinates - - //string message; - //string parameterInfo; // Line containing values for Qmass, dt, temperature - // for output to header - - - // !>> INITIALIZATION < fracStep; - for( ii=0;iimaxStep) - maxStep = pow(vel[ii].x,2)+pow(vel[ii].y,2)+pow(vel[ii].z,2); - Mathzone::Cartesian_to_Direct(vel[ii].x*dt/ucell.lat0,vel[ii].y*dt/ucell.lat0,vel[ii].z*dt/ucell.lat0, - ionlatvec.e11,ionlatvec.e12,ionlatvec.e13, - ionlatvec.e21,ionlatvec.e22,ionlatvec.e23, - ionlatvec.e31,ionlatvec.e32,ionlatvec.e33, - fracStep.x,fracStep.y,fracStep.z); - -// fracStep = ionlatvec.Inverse()*vel[ii]*dt/ucell.lat0; - taudirac[ii] = taudirac[ii] + fracStep; - } - - moveatoms(step); - string t("md_pos_"); - t=intTurnTostring(step,t); - connection2(); - printpos(t,step); - maxStep = sqrt(maxStep)*dt; -/* if(step1){ - PDF(step1); - printRDF(step1); - }*/ - - // (5) OFDFT optimizer - // Refresh the ionpositions, including the Ewald term - // and the local pseudopotentials term. - //RefreshIonPositions(grids); // This must be called every time the - // ion positions are changed - - // Get the new charge density in the new ion positions. - //Optimizer; //Optimize the density - //CalculateStress( energy, stress); - //PrintStress(stress); - - - // (8) - - - - // (9) Second thermostat step: updates vel, twiceKE, xLogS, vLogS -// cout<<"testNVT: x "<> INITIALIZATION <> FUNCTION BODY <> INTERIOR VARIABLES <* posd_in) +{ + int iat = 0; + for(int it = 0;it < this->ntype;it++) + { + Atom* atom = &this->atoms[it]; + for(int ia =0;ia< atom->na;ia++) + { + this->atoms[it].taud[ia] += posd_in[ia]; + iat++; + } + } + assert(iat == this->nat); + this->periodic_boundary_adjustment(); +} + void UnitCell::periodic_boundary_adjustment() { //---------------------------------------------- diff --git a/ABACUS.develop/source/src_pw/unitcell.h b/ABACUS.develop/source/src_pw/unitcell.h index 9d60a01af7..d634e20fce 100644 --- a/ABACUS.develop/source/src_pw/unitcell.h +++ b/ABACUS.develop/source/src_pw/unitcell.h @@ -67,6 +67,7 @@ class UnitCell const double& getNelec(void)const {return electrons_number;} void update_pos_tau(const double* pos); + void update_pos_taud(const Vector3* posd_in); void periodic_boundary_adjustment(); void bcast_atoms_tau(); void save_cartesian_position(double* pos)const;