Allink
v0.1
|
00001 #include "Forces.h" 00005 void Forces::SolveLeaves(){ 00006 AddRigid(); 00007 double *Known = (double *) calloc(pNPCh(),sizeof(double)); 00008 double *UnKnown = (double *) calloc(pNPCh(),sizeof(double)); 00009 for(int c=0;c<pNChain();c++){ 00010 int pInit = c*pNPCh(); 00011 int pEnd = (c+1)*pNPCh(); 00012 double Offset = 0.; 00013 for(int p=pInit;p<pEnd;p++) 00014 Known[p-pInit] = Pm[p].Pos[CNorm] - Offset; 00015 IntMatrix->Apply(Known,UnKnown); 00016 //IntMatrix->Solve(Known,UnKnown); 00017 for(int p=pInit;p<pEnd;p++){ 00018 int p1 = p-pInit; 00019 if(Pm[p].Typ != 0){continue;} 00020 Pm[p].Pos[CNorm] = UnKnown[p1] + Offset; 00021 } 00022 } 00023 free(Known); 00024 free(UnKnown); 00025 } 00029 void Forces::SolveRod(){ 00030 double *Known = (double *) calloc(pNPart(),sizeof(double)); 00031 double *UnKnown = (double *) calloc(pNPart(),sizeof(double)); 00032 double Offset = .5*pEdge(2); 00033 for(int p=0;p<pNPart();p++) 00034 Known[p] = Pm[p].Pos[CNorm] - Offset; 00035 IntMatrix->Apply(Known,UnKnown); 00036 //IntMatrix->Solve(Known,UnKnown); 00037 for(int p=0;p<pNPart();p++){ 00038 if(Pm[p].Typ != 0){continue;} 00039 Pm[p].Pos[CNorm] = UnKnown[p] + Offset; 00040 } 00041 free(Known); 00042 free(UnKnown); 00043 } 00047 void Forces::SolveLinksIterative(){ 00048 AddRigid(); 00049 //SmoothGrid(NEdge); 00050 double Inter = pEdge(CLat1)/(double)NEdge; 00051 SPLINE Weight; 00052 int NIter = 2000; 00053 Weight.a0 = Kf.El[2]; 00054 Weight.a1 = 0./Inter; 00055 Weight.a2 = Kf.Lap/SQR(Inter); 00056 Weight.a3 = 0./(Inter*SQR(Inter)); 00057 Weight.a4 = Kf.SLap/(SQR(Inter)*SQR(Inter)); 00058 int NDim = 2; 00059 Matrice *CoeffMatrix = new Matrice(Weight,NDim); 00060 double Offset = 0.; 00061 double *Known = (double *) calloc(pNPart(),sizeof(double)); 00062 double *UnKnown = (double *) calloc(pNPart(),sizeof(double)); 00063 double Sol = 0.; 00064 double Zed = 0.; 00065 int Link[2][5]; 00066 CoeffMatrix->Print(); 00067 for(int i=0;i<NIter;i++){ 00068 for(int p=0;p<pNPart();p++) 00069 Known[p] = Pm[p].Pos[CNorm] - Offset; 00070 for(int p=0;p<pNPart();p++){ 00071 if(Pm[p].Typ != 0){ 00072 UnKnown[p] = Known[p]; 00073 continue; 00074 } 00075 Sol = 0.; 00076 for(int d=0;d<2;d++){ 00077 Link[d][1] = Ln[p].Link[d*2]; 00078 Link[d][3] = Ln[p].Link[d*2+1]; 00079 Link[d][0] = Ln[Link[d][1]].Link[d*2]; 00080 Link[d][4] = Ln[Link[d][3]].Link[d*2+1]; 00081 for(int l=0,l1=-2;l<5;l++,l1++){ 00082 if(l==2){ 00083 l1 = 0; 00084 continue; 00085 } 00086 // if(!PeriodicImage[d]){ 00087 // if(d == 0){ 00088 // if(Link[d][l] != p+l1*nEdge[1]) continue; 00089 // if(Link[d][l] != p+l1) continue; 00090 // } 00091 // } 00092 Sol += CoeffMatrix->Val(2,l)*Pm[Link[d][l]].Pos[2]; 00093 } 00094 } 00095 UnKnown[p] = .4*Known[p] - .6*Sol/CoeffMatrix->Val(2,2); 00096 } 00097 for(int p=0;p<pNPart();p++){ 00098 if(Pm[p].Typ != 0){continue;} 00099 Pm[p].Pos[CNorm] = UnKnown[p] + Offset; 00100 } 00101 } 00102 free(Known); 00103 free(UnKnown); 00104 delete CoeffMatrix; 00105 } 00109 void Forces::SolveLinks(){ 00110 AddRigid(); 00111 FillMatrix(); 00112 double Offset = 0.; 00113 double *Known = (double *) calloc(pNPart(),sizeof(double)); 00114 double *UnKnown = (double *) calloc(pNPart(),sizeof(double)); 00115 for(int p=0;p<pNPart();p++) 00116 Known[p] = Pm[p].Pos[CNorm] - Offset; 00117 IntMatrix->Apply(Known,UnKnown); 00118 for(int p=0;p<pNPart();p++){ 00119 if(Pm[p].Typ != 0){continue;} 00120 Pm[p].Pos[CNorm] = UnKnown[p] + Offset; 00121 } 00122 free(Known); 00123 free(UnKnown); 00124 } 00125 // #include "compcol_double.h" 00126 // #include "comprow_double.h" 00127 // #include "ilupre_double.h" 00128 // #include "icpre_double.h" 00129 // #include "iotext_double.h" 00130 // void Forces::SolveLinksSparse(){ 00131 // int NEntries = 0; 00132 // int NColMax = pNPart(); 00133 // int NRowMax = pNPart(); 00134 // for(int p=0;p<pNPart();p++){ 00135 // if(Pm[p].Typ != 0){ 00136 // IntMatrix->Set(p,p,1.);Entries++; 00137 // continue; 00138 // } 00139 // int pym1 = Ln[p].Link[0]; 00140 // int pyp1 = Ln[p].Link[1]; 00141 // int pym2 = Ln[pym1].Link[0]; 00142 // int pyp2 = Ln[pyp1].Link[1]; 00143 // int pxm1 = Ln[p].Link[2]; 00144 // int pxp1 = Ln[p].Link[3]; 00145 // int pxm2 = Ln[pxm1].Link[2]; 00146 // int pxp2 = Ln[pxp1].Link[3]; 00147 // if(PeriodicImage[0]){ Entries += 4; 00148 // } 00149 // else{ 00150 // if(pxm2 == p-2*nEdge[1]) Entries++; 00151 // if(pxm1 == p-nEdge[1]) Entries++; 00152 // if(pxp1 == p+nEdge[1]) Entries++; 00153 // if(pxp2 == p+2*nEdge[1]) Entries++; 00154 // } 00155 // Entries++; 00156 // if(PeriodicImage[1]){Entries += 4; 00157 // } 00158 // else{ 00159 // if(pym2 == p-2) Entries++; 00160 // if(pym1 == p-1) Entries++; 00161 // if(pyp1 == p+1) Entries++; 00162 // if(pyp2 == p+2) Entries++; 00163 // } 00164 // } 00165 // double *MatVal = (double *)calloc(Entries,sizeof(double)); 00166 // int *ColIdx = (int *)calloc(Entries,sizeof(int)); 00167 // int *RowIdx = (int *)calloc(Entries,sizeof(int)); 00168 // for(int p=0,i=0;p<pNPart();p++){ 00169 // if(Pm[p].Typ != 0){ 00170 // ColIdx[i] = p; 00171 // RowIdx[i] = p; 00172 // MatVal[i] = 1.; 00173 // i++; 00174 // continue; 00175 // } 00176 // int pym1 = Ln[p].Link[0]; 00177 // int pyp1 = Ln[p].Link[1]; 00178 // int pym2 = Ln[pym1].Link[0]; 00179 // int pyp2 = Ln[pyp1].Link[1]; 00180 // int pxm1 = Ln[p].Link[2]; 00181 // int pxp1 = Ln[p].Link[3]; 00182 // int pxm2 = Ln[pxm1].Link[2]; 00183 // int pxp2 = Ln[pxp1].Link[3]; 00184 // // printf("%d)\n",p); 00185 // //printf("%d %d %d %d\n",pym2,pym1,pyp1,pyp2); 00186 // // printf("%d %d %d %d\n",pxm2,pxm1,pxp1,pxp2); 00187 // if(PeriodicImage[0]){ 00188 // RowIdx[i]=p;ColIdx[i]=pxm2;ValMat[i]=CoeffMatrix->Val(2,0);i++; 00189 // RowIdx[i]=p;ColIdx[i]=pxm1;ValMat[i]=CoeffMatrix->Val(2,1);i++; 00190 // RowIdx[i]=p;ColIdx[i]=pxp1;ValMat[i]=CoeffMatrix->Val(2,3);i++; 00191 // RowIdx[i]=p;ColIdx[i]=pxp2;ValMat[i]=CoeffMatrix->Val(2,4);i++; 00192 // } 00193 // else{ 00194 // if(pxm2 == p-2*nEdge[1]) 00195 // RowIdx[i]=p;ColIdx[i]=pxm2;ValMat[i]=CoeffMatrix->Val(2,0);i++; 00196 // if(pxm1 == p-nEdge[1]) 00197 // RowIdx[i]=p;ColIdx[i]=pxm1;ValMat[i]=CoeffMatrix->Val(2,1);i++; 00198 // if(pxp1 == p+nEdge[1]) 00199 // RowIdx[i]=p;ColIdx[i]=pxp1;ValMat[i]=CoeffMatrix->Val(2,3);i++; 00200 // if(pxp2 == p+2*nEdge[1]) 00201 // RowIdx[i]=p;ColIdx[i]=pxp2;ValMat[i]=CoeffMatrix->Val(2,4);i++; 00202 // } 00203 // IntMatrix->Add(p,p,CoeffMatrix->Val(2,2));Entries++; 00204 // if(PeriodicImage[1]){ 00205 // RowIdx[i]=p;ColIdx[i]=pym2;ValMat[i]=CoeffMatrix->Val(2,0);i++; 00206 // RowIdx[i]=p;ColIdx[i]=pym1;ValMat[i]=CoeffMatrix->Val(2,1);i++; 00207 // RowIdx[i]=p;ColIdx[i]=pyp1;ValMat[i]=CoeffMatrix->Val(2,3);i++; 00208 // RowIdx[i]=p;ColIdx[i]=pyp2;ValMat[i]=CoeffMatrix->Val(2,4);i++; 00209 // } 00210 // else{ 00211 // if(pym2 == p-2) 00212 // RowIdx[i]=p;ColIdx[i]=pym2;ValMat[i]=CoeffMatrix->Val(2,0);i++; 00213 // if(pym1 == p-1) 00214 // RowIdx[i]=p;ColIdx[i]=pym1;ValMat[i]=CoeffMatrix->Val(2,1);i++; 00215 // if(pyp1 == p+1) 00216 // RowIdx[i]=p;ColIdx[i]=pyp1;ValMat[i]=CoeffMatrix->Val(2,3);i++; 00217 // if(pyp2 == p+2) 00218 // RowIdx[i]=p;ColIdx[i]=pyp2;ValMat[i]=CoeffMatrix->Val(2,4);i++; 00219 // } 00220 // } 00221 // Coord_Mat_double C(NRowMax,NColMax,Entries,MatVal,RowIdx,ColIdx); 00222 // free(ColIdx); 00223 // free(RowIdx); 00224 // free(MatVal); 00225 // } 00226 // obsolete? 00227 // int Forces::Update(){ 00228 // for(int i=0;i<IntMax;i++){ 00229 // double Diff = Fm[Part2Move].Dir[2] - Fm[Part2Move].Ext[2]; 00230 // if(QUAD(Diff) < DiffForce ){ 00231 // printf("%d,%d) Force %lf= %lf - %lf Pos %lf \n",Part2Move,i,Diff,Fm[Part2Move].Dir[2],Fm[Part2Move].Ext[2],Pm[Part2Move].Pos[2]); 00232 // break; 00233 // } 00234 // double Sign=1.; 00235 // if( Diff < 0. ){ 00236 // Sign = -1.; 00237 // Pm[Part2Move].Pos[2] -= IncrDist; 00238 // } 00239 // else 00240 // Pm[Part2Move].Pos[2] += IncrDist; 00241 // for(int p=0,pp=Part2Move-1,ppp=Part2Move+1;p<pNPart();p++) 00242 // ; 00243 // if( Diff < 0. ){ 00244 // Pm[Part2Move].Pos[2] -= IncrDist; 00245 // } 00246 // else if(Diff > 0.){ 00247 // Pm[Part2Move].Pos[2] += IncrDist; 00248 // } 00249 // ForceFieldLine(); 00250 // Diff = Fm[Part2Move].Dir[2] - Fm[Part2Move].Ext[2]; 00251 // if(QUAD(Diff) < DiffForce ){ 00252 // printf("%d,%d) Force %lf= %lf - %lf Pos %lf \n",Part2Move,i,Diff,Fm[Part2Move].Dir[2],Fm[Part2Move].Ext[2],Pm[Part2Move].Pos[2]); 00253 // break; 00254 // } 00255 // if(Part2Move>0){ 00256 // if( Diff < 0. ){ 00257 // Pm[Part2Move-1].Pos[2] += IncrDist; 00258 // } 00259 // else if(Diff > 0.){ 00260 // Pm[Part2Move-1].Pos[2] -= IncrDist; 00261 // } 00262 // } 00263 // if(Part2Move<pNPart()-1){ 00264 // if( Diff < 0. ){ 00265 // Pm[Part2Move+1].Pos[2] += IncrDist; 00266 // } 00267 // else if(Diff > 0.){ 00268 // Pm[Part2Move+1].Pos[2] -= IncrDist; 00269 // } 00270 // } 00271 // ForceFieldLine(); 00272 // } 00273 // } 00274 // // obsolete? 00275 // int Forces::MinHelfrich(){ 00276 // SPLINE Par; 00277 // SPLINE Sp2; 00278 // double a1=0.; 00279 // double a2=0.; 00280 // double a3=0.; 00281 // double a4=0.; 00282 // double Ref=0.; 00283 // double Dx = pEdge(0)/(double)(NEdge-1); 00284 // for(int p=0;p<pNPart()-1;p++){ 00285 // if(p < 1){ 00286 // Sp2 = Mat->Forth(Pm[p].Pos,Pm[p+1].Pos,Pm[p+2].Pos,Pm[p+3].Pos,Pm[p+4].Pos,0,2); 00287 // Ref = Pm[p].Pos[0] - Pm[p+2].Pos[0]; 00288 // } 00289 // else if(p < 2){ 00290 // Sp2 = Mat->Forth(Pm[p-1].Pos,Pm[p].Pos,Pm[p+1].Pos,Pm[p+2].Pos,Pm[p+3].Pos,0,2); 00291 // Ref = Pm[p].Pos[0] - Pm[p+1].Pos[0]; 00292 // } 00293 // else if(p < pNPart()-2){ 00294 // Sp2 = Mat->Forth(Pm[p-2].Pos,Pm[p-1].Pos,Pm[p].Pos,Pm[p+1].Pos,Pm[p+2].Pos,0,2); 00295 // Ref = 0.; 00296 // } 00297 // else if(p == pNPart()-2){ 00298 // Sp2 = Mat->Forth(Pm[p-3].Pos,Pm[p-2].Pos,Pm[p-1].Pos,Pm[p].Pos,Pm[p+1].Pos,0,2); 00299 // Ref = Pm[p].Pos[0] - Pm[p-1].Pos[0]; 00300 // } 00301 // else if(p <= pNPart()-1){ 00302 // Sp2 = Mat->Forth(Pm[p-4].Pos,Pm[p-3].Pos,Pm[p-2].Pos,Pm[p-1].Pos,Pm[p].Pos,0,2); 00303 // Ref = Pm[p].Pos[0] - Pm[p-2].Pos[0]; 00304 // } 00305 // if(Pm[p].Typ == 1 || Pm[p].Typ == 2) 00306 // continue; 00307 // a2 = 2.*Sp2.a2 + 6.*Sp2.a3*Ref + 12.*Sp2.a4*Ref*Ref; 00308 // a4 = 24.*Sp2.a4; 00309 // a3 = a4*(12.*Dx*Dx - 24.*Kf.Lap/Kf.SLap) - 2.*a2; 00310 // //a3 = a4*(12.*Dx*Dx - 24.*.1) - 2.*a2; 00311 // a3 /= Dx; 00312 // a1 = Pm[p+1].Pos[2] - Pm[p].Pos[2] - a2*Dx*Dx - a3*Dx*Dx*Dx - a4*Dx*Dx*Dx*Dx; 00313 // a1 /= Dx; 00314 // double x = Pm[p+1].Pos[0] - Pm[p].Pos[0]; 00315 // printf("%d) %lf %lf %lf %lf -> %lf\n",p,a1,a2,a3,a4,Pm[p].Pos[2] + a1*x + a2*x*x + a3*x*x*x + a4*x*x*x*x); 00316 // Pm[p+1].Pos[2] = Pm[p].Pos[2] + a1*x + a2*x*x + a3*x*x*x + a4*x*x*x*x; 00317 // } 00318 // } 00319 //---------------------------------RIGID-------------------------- 00321 void Forces::VelVerletRigid(){ 00322 for(int n=0;n<pNNano();n++){ 00323 Vettore Axis(Nano[n].Axis,3); 00324 Vettore AMom(Nano[n].AMom,3); 00325 Vettore BackBone(3); 00326 Vettore VelTang(3); 00327 for(int d=0;d<3;d++){ 00328 BackBone.x[d] = Nano[n].Axis[d]*Nano->Height*.5; 00329 double Ran = Nano[n].Zeta * (2.*Mat->Casuale() - 1.); 00330 double Dis = - Nano[n].Gamma*Nano[n].AVel[d]; 00331 Nano[n].AMom[d] += Ran + Dis; 00332 } 00333 Matrice InTensor(3,3); 00334 Matrice RotT(3,3); 00335 Matrice Resp(3,3); 00336 Matrice Resp2(3,3); 00337 Vettore AVel(3); 00338 Vettore Normal(0.,0.,1.); 00339 Vettore Ax(3); 00340 Axis.VetV(&Axis,&Normal); 00341 double Angle = Ax.Angle(&Axis,&Normal); 00342 Quadri q(Ax.x,Angle); 00343 Matrice Rot(q,3); 00344 Rot.CopyOn(&RotT); 00345 RotT.Transpose(); 00346 InTensor.Set(0,0,1./(Nano->Mass*(.25*SQR(Nano->Rad)+1./12.*SQR(Nano->Height) ) ) ); 00347 InTensor.Set(1,1,1./(Nano->Mass*(.25*SQR(Nano->Rad)+1./12.*SQR(Nano->Height) ) ) ); 00348 InTensor.Set(2,2,1./(.5*Nano->Mass*SQR(Nano->Rad)) ); 00349 // Calculating r^t I^-1 r L = w 00350 Resp.Mult(RotT,InTensor); 00351 Resp2.Mult(Resp,Rot); 00352 // MatrVect(Resp2,Nano->AMom,AVel); 00353 00354 //printf("%d) %d\n",n,Gen->Step); 00355 for(int d=0;d<3;d++){ 00356 double tmp = .5*Nano[n].Force[d]*pDeltat()/Nano[n].Mass; 00357 Nano[n].Vel[d] += tmp; 00358 Nano[n].AVel[d] += Nano[n].AMom[d]/Nano[n].Mass*.01; 00359 Nano[n].Pos[d] += Nano[n].Vel[d]*pDeltat(); 00360 Nano[n].Pos[d] -= floor(Nano[n].Pos[d]/pEdge(d))*pEdge(d); 00361 } 00362 if(Nano[n].Shape != 2) continue; 00363 Vettore Omega(Nano[n].AVel,3); 00364 for(int d=0;d<3;d++) 00365 BackBone.x[d] = Nano[n].Height*.5*Nano[n].Axis[d]; 00366 VelTang.VetV(&Omega,&BackBone); 00367 for(int d=0;d<3;d++){ 00368 BackBone.x[d] += VelTang.x[d]*pDeltat(); 00369 Axis.x[d] = BackBone.x[d]; 00370 } 00371 Axis.Normalize(); 00372 Axis.Export(Nano[n].Axis); 00373 //printf("%lf %lf %lf\n",Nano[n].Vel[0],Nano[n].Vel[1],Nano[n].Vel[2]); 00374 //printf("%lf %lf %lf\n",Nano[n].Force[0],Nano[n].Force[1],Nano[n].Force[2]); 00375 //printf("%lf %lf %lf\n",Nano[n].Pos[0],Nano[n].Pos[1],Nano[n].Pos[2]); 00376 //printf("%lf %lf %lf\n",Nano[n].AMom[0],Nano[n].AMom[1],Nano[n].AMom[2]); 00377 } 00378 } 00382 void Forces::VelVerletRigid2(){ 00383 for(int n=0;n<pNNano();n++) { 00384 for(int d=0;d<3;d++){ 00385 Nano[n].AVel[d] += .5*Nano[n].AMom[d]; 00386 Nano[n].Vel[d] += .5*Nano[n].Force[d]*pDeltat()/Nano[n].Mass; 00387 } 00388 } 00389 } 00390 //------------------------------------------------------------ 00391 //-------------------------MONTE-CARLO------------------------ 00392 //------------------------------------------------------------ 00394 int Forces::IfMetropolis(double Arg,double Weight){ 00395 if(exp(pBeta()*Arg)*Weight > 1. ) return 1; 00396 double Ran = Mat->Casuale(); 00397 if(exp(pBeta()*Arg)*Weight > Ran ){ 00398 return 1; 00399 } 00400 return 0; 00401 } 00402 //-----------------Single-particle---------------------------- 00404 int Forces::InsertBead(int p){ 00405 Pm[p].Pos[0] = pEdge(0)*Mat->Casuale(); 00406 Pm[p].Pos[1] = pEdge(1)*Mat->Casuale(); 00407 Pm[p].Pos[2] = pEdge(2)*Mat->Casuale(); 00408 Pc->AddPart(p,Pm[p].Pos); 00409 } 00413 int Forces::TryInsert(){ 00414 int p = pNPart(); 00415 ReSetNPart(pNPart()+1); 00416 InsertBead(p); 00417 double Pot[3]; 00418 double NrgDiff = CalcNrgBead(p,Pot); 00419 double Arg = ChemPotId + ChemPotEx - NrgDiff; 00420 double Weight = pVol()/(double)(pNPart()+1); 00421 if( !IfMetropolis(Arg,Weight) ){ 00422 Pc->RemPart(p,Pm[p].Pos); 00423 ReSetNPart(pNPart()-1); 00424 return 0; 00425 } 00426 //printf("Added a particle %d\n",p); 00427 return 1; 00428 } 00432 int Forces::TryRemove(){ 00433 printf("remove\n"); 00434 int p = (int)(Mat->Casuale()*pNPart()); 00435 double Pot[3]; 00436 double NrgDiff = CalcNrgBead(p,Pot); 00437 double Arg = - ChemPotId - ChemPotEx - NrgDiff; 00438 if( !IfMetropolis(Arg,pNPart()/pVol()) ){ 00439 return 0; 00440 } 00441 SwapPart(p,pNPart()-1); 00442 Pc->SwapPart(p,Pm[p].Pos,pNPart()-1,Pm[pNPart()-1].Pos); 00443 Pc->RemPart(pNPart()-1,Pm[pNPart()-1].Pos); 00444 ReSetNPart(pNPart()-1); 00445 return 1; 00446 } 00448 int Forces::MoveBead(int p){ 00449 for(int d=0;d<3;d++){ 00450 Pm[p].Pos[d] += Mat->Gaussiano(0.,GaussVar); 00451 Pm[p].Pos[d] -= floor(Pm[p].Pos[d]*pInvEdge(d))*pEdge(d); 00452 } 00453 } 00457 int Forces::TryMove(){ 00458 int p = (int)(Mat->Casuale()*pNPart()); 00459 if(Pm[p].Typ >= 2) return 1; 00460 //old situa 00461 double Pos[3] = {Pm[p].Pos[0],Pm[p].Pos[1],Pm[p].Pos[2]}; 00462 double Pot[3] = {0.,0.,0.}; 00463 double Nrg0 = CalcNrgBead(p,Pot); 00464 //RemDens(p,p+1); 00465 //double Nrg0 = OldNrgPm[p*3] + OldNrgPm[p*3+1] + OldNrgPm[p*3+2]; 00466 //new situa 00467 MoveBead(p); 00468 Pc->MovePart(p,Pos,Pm[p].Pos); 00469 //AddDens(p,p+1); 00470 double Nrg1 = CalcNrgBead(p,Pot); 00471 //like the new situa? 00472 double NrgDiff = Nrg1 - Nrg0; 00473 if(!IfMetropolis(-NrgDiff,1.)){ 00474 //RemDens(p,p+1); 00475 Pc->MovePart(p,Pm[p].Pos,Pos); 00476 for(int d=0;d<3;d++) Pm[p].Pos[d] = Pos[d]; 00477 //AddDens(p,p+1); 00478 return 0; 00479 } 00480 //OldNrgSys = SumDens(0,pNPart()); 00481 OldNrgSys -= Pot[2];//DensFuncNrgCh(c); 00482 return 1; 00483 } 00484 //-----------------------------Chains--------------------- 00488 void Forces::StudySys(){ 00489 //getting the distribution 00490 double Norm = 0.; 00491 double *LineS = new double[NBin]; 00492 for(int i=0;i<NBin;i++){ 00493 FirstBeadDistr[i] = 0.; 00494 } 00495 for(int c=0;c<pNChain();c++){ 00496 int p1 = c*pNPCh(); 00497 int i = (int)(Pm[p1].Pos[CNorm]*NBin*pInvEdge(CNorm)); 00498 if(i < 0 || i >= NBin) continue; 00499 FirstBeadDistr[i] += 1.; 00500 Norm += 1.; 00501 } 00502 //normalizing and smoothing 00503 for(int v=0;v<NBin;v++) LineS[v] = FirstBeadDistr[v]; 00504 InterBSpline1D(LineS,FirstBeadDistr,NBin,NBin); 00505 for(int v=0;v<NBin;v++) LineS[v] = FirstBeadDistr[v]; 00506 InterBSpline1D(LineS,FirstBeadDistr,NBin,NBin); 00507 Norm = Norm >= 0. ? 1./Norm : 1.; 00508 for(int i=0;i<NBin;i++){ 00509 FirstBeadDistr[i] *= Norm; 00510 } 00511 //cumulative 00512 for(int i=1;i<NBin;i++){ 00513 FirstBeadDistr[i] += FirstBeadDistr[i-1]; 00514 if(FirstBeadDistr[i] > .25 && FirstBeadDistr[i-1] < .25) 00515 BorderBias[0] = i/NBin*pEdge(CNorm); 00516 else if(FirstBeadDistr[i] > .75 && FirstBeadDistr[i-1] < .75) 00517 BorderBias[1] = i/NBin*pEdge(CNorm); 00518 } 00519 delete [] LineS; 00520 } 00524 void Forces::ConsiderCh(int c){ 00525 int p1 = c*pNPCh(); 00526 for(int p=0;p<pNPCh();p++) Pc->AddPart(p+p1,Pm[p+p1].Pos); 00527 AddDens(p1,p1+pNPCh()); 00528 } 00532 void Forces::IgnoreCh(int c){ 00533 int p1 = c*pNPCh(); 00534 RemDens(p1,p1+pNPCh()); 00535 for(int p=0;p<pNPCh();p++) Pc->RemPart(p+p1,Pm[p+p1].Pos); 00536 } 00540 void Forces::RemChFromSys(int c){ 00541 int c2 = pNChain()-1; 00542 int p1 = c*pNPCh(); 00543 int p2 = c2*pNPCh(); 00544 RemDens(p1,p1+pNPCh()); 00545 if(c != c2){ 00546 for(int e=0;e<3;e++) 00547 OldNrgCh[c*3+e] = OldNrgCh[c2*3+e]; 00548 RemDens(p2,p2+pNPCh()); 00549 // for(int p=0;p<pNPCh();p++) 00550 // Pc->RemPart(p2+p,Pm[p2+p].Pos); 00551 // for(int p=0;p<pNPCh();p++) 00552 // Pc->RemPart(p1+p,Pm[p1+p].Pos); 00553 // SwapChain(c,pNChain()-1); 00554 // for(int p=0;p<pNPCh();p++) 00555 // Pc->AddPart(p1+p,Pm[p1+p].Pos); 00556 for(int p=0;p<pNPCh();p++) 00557 Pc->SwapPart(p+p1,Pm[p+p1].Pos,p2+p,Pm[p2+p].Pos); 00558 SwapChain(c,pNChain()-1); 00559 AddDens(p1,p1+pNPCh()); 00560 } 00561 for(int p=0;p<pNPCh();p++) 00562 Pc->RemPart(p2+p,Pm[p2+p].Pos); 00563 ReSetNPart(pNPart()-pNPCh()); 00564 ReSetNChain(pNChain()-1); 00565 } 00569 void Forces::SaveCh(int c){ 00570 int p1 = c*pNPCh(); 00571 for(int p=0;p<pNPCh();p++){ 00572 for(int d=0;d<3;d++){ 00573 OldPos[p][d] = Pm[p+p1].Pos[d]; 00574 } 00575 } 00576 } 00580 void Forces::ReInsertCh(int c){ 00581 IgnoreCh(c); 00582 int p1 = c*pNPCh(); 00583 //old situa 00584 for(int p=0;p<pNPCh();p++){ 00585 for(int d=0;d<3;d++){ 00586 Pm[p+p1].Pos[d] = OldPos[p][d]; 00587 } 00588 } 00589 ConsiderCh(c); 00590 } 00592 double Forces::InsertCh(int c){ 00593 int p1 = c*pNPCh(); 00594 double Weight = 1.; 00595 ReSetNPart(pNPart()+pNPCh()); 00596 ReSetNChain(pNChain()+1); 00597 Pm[p1].Pos[CLat1] = Mat->Casuale()*pEdge(CLat1); 00598 Pm[p1].Pos[CLat2] = Mat->Casuale()*pEdge(CLat2); 00599 Pm[p1].Pos[CNorm] = Mat->Casuale()*pEdge(CNorm); 00600 if(VAR_IF_TYPE(CalcMode,CALC_BIL_BIAS)){ 00601 Pm[p1].Pos[CNorm] = Mat->Casuale()*(BorderBias[1] - BorderBias[0]) + BorderBias[0]; 00602 //Mat->RandDiscrProb(FirstBeadDistr,NBin)*pEdge(CNorm); 00603 Weight *= (BorderBias[1]-BorderBias[0])*pEdge(CLat1)*pEdge(CLat2)/pVol(); 00604 } 00605 else if(VAR_IF_TYPE(CalcMode,CALC_SPH_BIAS)){ 00606 double Incr = 0.2; 00607 double z = 2.0 * Mat->Casuale() - 1.0; 00608 double t = 2.0 * M_PI * Mat->Casuale(); 00609 double w = sqrt( 1 - z*z ); 00610 double x = w * cos( t ); 00611 double y = w * sin( t ); 00612 double Rad = Mat->Casuale()*Incr + Nano->Rad; 00613 Pm[p1].Pos[CLat1] = x*Rad + Nano->Pos[0]; 00614 Pm[p1].Pos[CLat2] = y*Rad + Nano->Pos[1]; 00615 Pm[p1].Pos[CNorm] = z*Rad + Nano->Pos[2]; 00616 double Vol = 4./3.*M_PI*( CUBE(Nano->Rad + Incr) - CUBE(Nano->Rad)); 00617 Weight *= Vol/pVol(); 00618 } 00619 Weight *= InsertRest(p1,0); 00620 // for(int p=0;p<pNPCh();p++){ 00621 // fprintf(StatFile1,"%lf %lf %lf 0. 0. 0. %d\n",Pm[p1+p].Pos[0],Pm[p1+p].Pos[1],Pm[p1+p].Pos[2],pType(p+p1)); 00622 // } 00623 // fflush(StatFile1); 00624 ConsiderCh(c); 00625 return Weight; 00626 } 00628 double Forces::InsertRest(int pCurr,int StartPos){ 00629 double Weight = 1.; 00630 for(int p=StartPos+1;p<pNPCh();p++){ 00631 for(int d=0;d<3;d++){ 00632 double Ran = Mat->Gaussiano(0.,GaussVar); 00633 Pm[p+pCurr].Pos[d] = Pm[p-1+pCurr].Pos[d] + Ran; 00634 Pm[p+pCurr].Pos[d] -= floor(Pm[p+pCurr].Pos[d]*pInvEdge(d))*pEdge(d); 00635 } 00636 } 00637 for(int p=StartPos-1;p>=0;p--){ 00638 for(int d=0;d<3;d++){ 00639 double Ran = Mat->Gaussiano(0.,GaussVar); 00640 Pm[p+pCurr].Pos[d] = Pm[p+1+pCurr].Pos[d] + Ran; 00641 Pm[p+pCurr].Pos[d] -= floor(Pm[p+pCurr].Pos[d]*pInvEdge(d))*pEdge(d); 00642 } 00643 } 00644 return Weight; 00645 } 00649 int Forces::TryMoveCh(){ 00650 int c = (int)(Mat->Casuale()*pNChain()); 00651 int p1 = c*pNPCh(); 00652 double Pot[3]; 00653 // old situa 00654 SaveCh(c); 00655 IgnoreCh(c); 00656 double NrgOld = CalcNrgCh(c,Pot); 00657 // new situa 00658 ReSetNPart(pNPart()-pNPCh()); 00659 ReSetNChain(pNChain()-1); 00660 InsertCh(c); 00661 double NrgNew = CalcNrgCh(c,Pot); 00662 //like the new situa? 00663 double NrgDiff = NrgNew - NrgOld; 00664 if(!IfMetropolis(-NrgDiff,1.)){ 00665 ReInsertCh(c); 00666 return 0; 00667 } 00668 OldNrgCh[c*3+2] = NrgNew; 00669 OldNrgSys += NrgDiff; 00670 return 1; 00671 } 00675 int Forces::TryRemoveCh(){ 00676 if(pNPart() <= 0) return 0; 00677 int c = (int)(Mat->Casuale()*pNChain()); 00678 int p1 = c*pNPCh(); 00679 double Pot[3]; 00680 //like the new situa? 00681 double NrgDiff = CalcNrgCh(c,Pot); 00682 //double NrgDiff = OldNrgCh[c*3+2]; 00683 //fprintf(StatFile1,"%lf\n",NrgDiff); 00684 //fflush(StatFile1); 00685 double Arg = -ChemPotId -ChemPotEx +NrgDiff; 00686 double Weight = pNChain()/pVol(); 00687 if(!IfMetropolis(Arg,Weight) ){ 00688 return 0; 00689 } 00690 RemChFromSys(c); 00691 OldNrgSys -= NrgDiff; 00692 return 1; 00693 } 00697 int Forces::TryInsertCh(){ 00698 //old situa 00699 int c = pNChain(); 00700 int p1 = c*pNPCh(); 00701 double Pot[3]; 00702 //new situa 00703 InsertCh(c); 00704 //like the new situa? 00705 double NrgDiff = CalcNrgCh(c,Pot); 00706 //fprintf(StatFile2,"%lf\n",NrgDiff); 00707 fflush(StatFile2); 00708 //printf("add %lf sys %lf\n",NrgDiff,OldNrgSys); 00709 double Arg = ChemPotId + ChemPotEx - NrgDiff; 00710 double Weight = pVol()/(double)(pNChain()+1); 00711 //printf("Ins %lf\n",NrgDiff); 00712 if(!IfMetropolis(Arg,Weight)){ 00713 RemChFromSys(c); 00714 return 0; 00715 } 00716 //printf("accepted\n"); 00717 //printf("Inserted %lf\n",NrgDiff); 00718 OldNrgCh[c*3+2] = NrgDiff; 00719 OldNrgSys += NrgDiff; 00720 return 1; 00721 } 00722 //---------------------------Bias------------------------------- 00724 double Forces::RemoveChBias(int c){ 00725 int p1 = c*pNPCh(); 00726 RemDens(p1,p1+pNPCh()); 00727 for(int p=0;p<pNPCh();p++) Pc->RemPart(p+p1,Pm[p+p1].Pos); 00728 double NrgDiff = DensFuncNrgGhost(Pm[p1].Pos,p1,Pm[p1].Typ); 00729 //fprintf(StatFile1,"%lf %lf\n",NrgDiff,NanoNrg(p1)); 00730 NrgDiff += CalcBendingGhost(Pm[p1].Pos,p1); 00731 NrgDiff += NanoNrg(p1); 00732 double Weight = exp(-NrgDiff+NrgPBead); 00733 Pc->AddPart(p1,Pm[p1].Pos); 00734 AddDens(p1,p1+1); 00735 for(int p=p1+1;p<p1+pNPCh();p++){ 00736 Weight *= WeightSetBond(p,Pm[p].Typ); 00737 Pc->AddPart(p,Pm[p].Pos); 00738 AddDens(p,p+1); 00739 } 00740 return Weight; 00741 } 00743 double Forces::WeightSetBond(int p,int Type){ 00744 double NrgDiff = DensFuncNrgGhost(Pm[p].Pos,p,Pm[p].Typ); 00745 NrgDiff += CalcBendingGhost(Pm[p].Pos,p); 00746 NrgDiff += NanoNrg(p); 00747 CumProbBias[0] = exp(-NrgDiff+NrgPBead); 00748 for(int t=1;t<NTrialBias;t++){ 00749 for(int d=0;d<3;d++){ 00750 BondPosBias[t][d] = Pm[p-1].Pos[d] + Mat->Gaussiano(0.,GaussVar); 00751 BondPosBias[t][d] -= floor(BondPosBias[t][d]*pInvEdge(d))*pEdge(d); 00752 } 00753 NrgDiff = DensFuncNrgGhost(BondPosBias[t],p,Type); 00754 //fprintf(StatFile1,"%lf %lf\n",NrgDiff,NanoNrg(BondPosBias[t],Type)); 00755 NrgDiff += CalcBendingGhost(BondPosBias[t],p); 00756 NrgDiff += NanoNrg(BondPosBias[t],Type); 00757 CumProbBias[t] = exp(-NrgDiff+NrgPBead); 00758 } 00759 double Weight = 0.; 00760 for(int t=0;t<NTrialBias;t++){ 00761 Weight += CumProbBias[t]; 00762 } 00763 return Weight/(double)NTrialBias; 00764 } 00766 double Forces::InsertChBias(int c){ 00767 int p1 = c*pNPCh(); 00768 double Weight = 1.; 00769 ReSetNPart(pNPart()+pNPCh()); 00770 ReSetNChain(pNChain()+1); 00771 Pm[p1].Pos[CLat1] = Mat->Casuale()*pEdge(CLat1); 00772 Pm[p1].Pos[CLat2] = Mat->Casuale()*pEdge(CLat2); 00773 Pm[p1].Pos[CNorm] = Mat->Casuale()*pEdge(CNorm); 00774 if(VAR_IF_TYPE(CalcMode,CALC_BIL_BIAS)){ 00775 Pm[p1].Pos[CNorm] = Mat->Casuale()*(BorderBias[1] - BorderBias[0]) + BorderBias[0]; 00776 //Mat->RandDiscrProb(FirstBeadDistr,NBin)*pEdge(CNorm); 00777 Weight *= (BorderBias[1]-BorderBias[0])*pEdge(CLat1)*pEdge(CLat2)/pVol(); 00778 } 00779 else if(VAR_IF_TYPE(CalcMode,CALC_SPH_BIAS)){ 00780 double Incr = 0.2; 00781 double z = 2.0 * Mat->Casuale() - 1.0; 00782 double t = 2.0 * M_PI * Mat->Casuale(); 00783 double w = sqrt( 1 - z*z ); 00784 double x = w * cos( t ); 00785 double y = w * sin( t ); 00786 double Rad = Mat->Casuale()*Incr + Nano->Rad; 00787 Pm[p1].Pos[CLat1] = x*Rad + Nano->Pos[0]; 00788 Pm[p1].Pos[CLat2] = y*Rad + Nano->Pos[1]; 00789 Pm[p1].Pos[CNorm] = z*Rad + Nano->Pos[2]; 00790 double Vol = 4./3.*M_PI*( CUBE(Nano->Rad + Incr) - CUBE(Nano->Rad)); 00791 Weight *= Vol/pVol(); 00792 //fprintf(StatFile2,"%lf %lf %lf %d\n",Pm[p1].Pos[0],Pm[p1].Pos[1],Pm[p1].Pos[2],pType(p1)); 00793 //fflush(StatFile2); 00794 } 00795 double NrgDiff = DensFuncNrgGhost(Pm[p1].Pos,p1,Pm[p1].Typ); 00796 fprintf(StatFile2,"%lf %lf\n",NrgDiff,NanoNrg(p1)); 00797 NrgDiff += CalcBendingGhost(Pm[p1].Pos,p1); 00798 NrgDiff += NanoNrg(p1); 00799 Weight *= exp(-NrgDiff+NrgPBead); 00800 // printf("Weight1 %lf %lf\n",NrgDiff,Weight); 00801 Pc->AddPart(p1,Pm[p1].Pos); 00802 AddDens(p1,p1+1); 00803 for(int p=p1+1;p<(c+1)*pNPCh();p++){ 00804 double Weight1 = CreateSetBond(p,Pm[p].Typ); 00805 Weight *= Weight1; 00806 Pc->AddPart(p,Pm[p].Pos); 00807 AddDens(p,p+1); 00808 } 00809 // for(int p=0;p<pNPCh();p++){ 00810 // fprintf(StatFile1,"%lf %lf %lf %d\n",Pm[p1+p].Pos[0],Pm[p1+p].Pos[1],Pm[p1+p].Pos[2],pType(p+p1)); 00811 // } 00812 // fflush(StatFile1); 00813 return Weight; 00814 } 00816 double Forces::CreateSetBond(int p,int Type){ 00817 int tChoosen = 0; 00818 for(int t=0;t<NTrialBias;t++){ 00819 for(int d=0;d<3;d++){ 00820 BondPosBias[t][d] = Pm[p-1].Pos[d] + Mat->Gaussiano(0.,GaussVar); 00821 BondPosBias[t][d] -= floor(BondPosBias[t][d]*pInvEdge(d))*pEdge(d); 00822 } 00823 double NrgDiff = DensFuncNrgGhost(BondPosBias[t],p,Type); 00824 fprintf(StatFile2,"%lf %lf\n",NrgDiff,NanoNrg(BondPosBias[t],Type)); 00825 NrgDiff += CalcBendingGhost(BondPosBias[t],p); 00826 NrgDiff += NanoNrg(BondPosBias[t],Type); 00827 CumProbBias[t] = exp(-NrgDiff+NrgPBead); 00828 } 00829 double Weight = 0.; 00830 for(int t=0;t<NTrialBias;t++){ 00831 Weight += CumProbBias[t]; 00832 } 00833 CumProbBias[0] /= Weight; 00834 double Ran = Mat->Casuale(); 00835 for(int t=1;t<NTrialBias;t++){ 00836 CumProbBias[t] /= Weight; 00837 CumProbBias[t] += CumProbBias[t-1]; 00838 } 00839 for(int t=0;t<NTrialBias;t++){ 00840 if(Ran < CumProbBias[t]){ 00841 tChoosen = t; 00842 break; 00843 } 00844 } 00845 for(int d=0;d<3;d++){ 00846 Pm[p].Pos[d] = BondPosBias[tChoosen][d]; 00847 Pm[p].Pos[d] -= floor(Pm[p].Pos[d]*pInvEdge(d))*pEdge(d); 00848 } 00849 return Weight/(double)NTrialBias; 00850 } 00854 int Forces::TryRemoveChBias(){ 00855 if(pNPart() <= 0) return 0; 00856 int c = (int)(Mat->Casuale()*pNChain()); 00857 int p1 = c*pNPCh(); 00858 double Weight1 = RemoveChBias(c); 00859 double Arg = - ChemPotId - ChemPotEx ; 00860 double Weight = pNChain()/(Weight1*pVol()); 00861 //printf("rem %lf\n",Weight1); 00862 //fprintf(TempFile,"1 %lf\n",NrgDiff); 00863 if(!IfMetropolis(Arg,Weight)){ 00864 return 0; 00865 } 00866 //fprintf(TempFile,"2 %lf\n",NrgDiff); 00867 RemChFromSys(c); 00868 return 1; 00869 } 00873 int Forces::TryInsertChBias(){ 00874 //add one chain 00875 int c = pNChain(); 00876 int p1 = c*pNPCh(); 00877 double Weight1 = InsertChBias(c); 00878 double Arg = ChemPotId + ChemPotEx; 00879 double Weight = Weight1*pVol()/(double)(pNChain()+1); 00880 if(!IfMetropolis(Arg,Weight)){ 00881 RemChFromSys(c); 00882 return 0; 00883 } 00884 return 1; 00885 } 00886 //-------------------WIDOM-------------------------- 00890 void Forces::WidomInsert(double *NrgDiff){ 00891 int p1 = pNPart(); 00892 InsertBead(p1); 00893 *NrgDiff = DensFuncNrgGhost(Pm[p1].Pos,p1,Pm[p1].Typ); 00894 *NrgDiff += CalcBendingGhost(Pm[p1].Pos,p1); 00895 *NrgDiff += NanoNrg(p1); 00896 Pc->RemPart(p1,Pm[p1].Pos); 00897 } 00901 void Forces::WidomRemove(double *NrgDiff,int p){ 00902 double Pot[3]; 00903 *NrgDiff = CalcNrgBead(p,Pot); 00904 } 00908 void Forces::WidomInsertCh(double *NrgDiff){ 00909 int c = pNChain(); 00910 int p1 = c*pNPCh(); 00911 InsertCh(c); 00912 CalcNrgCh(c,NrgDiff); 00913 RemChFromSys(c); 00914 } 00918 void Forces::WidomRemoveCh(double *NrgDiff,int c){ 00919 NrgDiff[0] = OldNrgCh[c*3 ]; 00920 NrgDiff[1] = OldNrgCh[c*3+1]; 00921 NrgDiff[2] = OldNrgCh[c*3+2]; 00922 } 00926 void Forces::WidomBiasChIn(double *Weight){ 00927 int c = pNChain(); 00928 int p1 = c*pNPCh(); 00929 *Weight = InsertChBias(c); 00930 RemChFromSys(c); 00931 } 00935 void Forces::WidomBiasChOut(double *Weight,int c){ 00936 *Weight = RemoveChBias(c); 00937 } 00938 //----------------------MOLECULAR-DYNAMICS---------------------- 00942 void Forces::VelVerlet1(){ 00943 for(int p=0;p<pNPart();p++){ 00944 if(Pm[p].Typ != 0) continue; 00945 for(int d=0;d<3;d++){ 00946 //if(fabs(Fm[p].Dir[d]) > 500.) continue; 00947 Pm[p].Vel[d] += .5*(Fm[p].Dir[d] + Fm[p].Ext[d])*pDeltat(); 00948 Pm[p].Pos[d] += Pm[p].Vel[d]*pDeltat(); 00949 Pm[p].Pos[d] -= floor(Pm[p].Pos[d]*pInvEdge(d))*pEdge(d); 00950 //printf("%d %d) %lf %g %lf\n",p,d,Pm[p].Pos[d],Fm[p].Dir[d],Pm[p].Vel[d]); 00951 } 00952 } 00953 } 00957 void Forces::LangevinTherm(){ 00958 double Gamma = Viscosity;//3.*3.14*10.*Viscosity; 00959 double Zeta = sqrt(12.*2.*1.*Gamma/pDeltat()); 00960 for(int p=0;p<pNPart();p++){ 00961 for(int d=0;d<3;d++){ 00962 Fm[p].Dir[d] += Zeta*(2.*Mat->Casuale() - 1.); 00963 //Fm[p].Dir[d] += Zeta*Mat->Gaussiano(0.,1.); 00964 Fm[p].Dir[d] -= Gamma*Pm[p].Vel[d]; 00965 } 00966 } 00967 } 00971 void Forces::AndersenTherm(){ 00972 double Sigma = sqrt(pTemp()); 00973 for(int p=0;p<pNPart();p++){ 00974 if(Mat->Casuale() < pDeltat()){ 00975 for(int d=0;d<3;d++){ 00976 Pm[p].Vel[d] = Mat->Gaussiano(0.,Sigma); 00977 } 00978 } 00979 } 00980 } 00984 void Forces::BerendsenTherm(){ 00985 double Temp = 0.; 00986 for(int p=0;p<pNPart();p++){ 00987 for(int d=0;d<3;d++){ 00988 Pm[p].Vel[d] += .5*Fm[p].Dir[d]*pDeltat(); 00989 Temp += SQR(Pm[p].Vel[d]); 00990 } 00991 } 00992 Temp = Temp/(3*pNPart()); 00993 double Norm = 1./sqrt(Temp); 00994 for(int p=0;p<pNPart();p++){ 00995 for(int d=0;d<3;d++){ 00996 Pm[p].Vel[d] *= Norm; 00997 } 00998 } 00999 } 01003 void Forces::ChooseThermostat(int Mode){ 01004 printf("Thermostat: "); 01005 if(Mode==THERM_LANG){ 01006 CalcTherm = &Forces::LangevinTherm; 01007 printf("Langevin\n"); 01008 } 01009 else if((Mode==THERM_AND)){ 01010 CalcTherm = &Forces::AndersenTherm; 01011 printf("Andersen\n"); 01012 } 01013 else if((Mode==THERM_BERE)){ 01014 CalcTherm = &Forces::BerendsenTherm; 01015 printf("Berendsen\n"); 01016 } 01017 else if((Mode==THERM_NO)){ 01018 CalcTherm = &Forces::NoTherm; 01019 printf("no thermostat\n"); 01020 } 01021 else{ 01022 printf("mode not present\n"); 01023 exit(1); 01024 } 01025 } 01029 void Forces::VelVerlet2(){ 01030 for(int p=0;p<pNPart();p++){ 01031 for(int d=0;d<3;d++){ 01032 Pm[p].Vel[d] += .5*(Fm[p].Dir[d] + Fm[p].Ext[d])*pDeltat(); 01033 Fm[p].Dir[d] = 0.; 01034 } 01035 } 01036 }