Esempio n. 1
0
void InfoModel::ModelWithCluster( InfoModel &model, Clusters &cluster )
{
	model.energy = cluster.GetEnergy();
	model.N = cluster.GetAtomsNumber();
	model.alloy = cluster.GetAlloy();
	model.alloyNum = cluster.GetAlloyNum();
}
double GuptaPotentialEnergy::EnergyValue(Clusters& cluster)
{
	int N = cluster.GetAtomsNumber();
	_atomEnergy.resize(N);
	double *dis = cluster.GetDistancePointer();
	double E = 0;
	vector<double> VEN(N,0);
	vector<double> PEN(N,0);
	
	Alloy alloy = cluster.GetAlloy();

	for (int i = 0; i < N - 1; i ++)
	{
		for (int j = i + 1; j < N; j ++)
		{
			double r = dis[ i * N + j ];
			int note1 = cluster.GetAtomAtIndex(i).GetNote();
			int note2 = cluster.GetAtomAtIndex(j).GetNote();
			Gupta_AtomParamter parameter = (Gupta_AtomParamter&)ReturnAtomParameter(alloy[note1],alloy[note2]);
			double FMJN = r / parameter.r0 - 1;
			double FMJV = parameter.A * exp( -parameter.P * FMJN );
			double FMJP  = parameter.Xi * parameter.Xi * exp( -2 * parameter.q *FMJN );

			VEN[i] += FMJV;
			VEN[j] += FMJV;
			PEN[i] += FMJP;
			PEN[j] += FMJP;
		}
	}
	for (int i = 0; i < N; i++)
	{		
		_atomEnergy[i] = VEN[i] - sqrt(PEN[i]);
		E += _atomEnergy[i];
	}

	cluster.SetEnergyVectorOfAtoms(_atomEnergy);
	cluster.SetEnergy(E);

	return E;
}
double GuptaPotentialEnergy::ForceValue(Clusters& cluster)
{
	int N = cluster.GetAtomsNumber();
	double *dis = cluster.GetDistancePointer();
	vector<double> PEN(N,0);
	Alloy alloy = cluster.GetAlloy();

	for (int i = 0; i < N - 1; i ++)
	{
		for (int j = i + 1; j < N; j ++)
		{
			double r = dis[ i * N + j ];
			int note1 = cluster.GetAtomAtIndex(i).GetNote();
			int note2 = cluster.GetAtomAtIndex(j).GetNote();
			Gupta_AtomParamter parameter = (Gupta_AtomParamter&)ReturnAtomParameter(alloy[note1],alloy[note2]);
			double FMJN = r / parameter.r0 - 1;
			double FMJP  = parameter.Xi * parameter.Xi * exp( -2 * parameter.q *FMJN );

			PEN[i] += FMJP;
			PEN[j] += FMJP;
		}
	}

	for (int i = 0; i < N; i++)
		PEN[i] = 1/sqrt(PEN[i])/2;

	_atomForceAlongX.resize(N);
	_atomForceAlongY.resize(N);
	_atomForceAlongZ.resize(N);
	_atomForceAlongX.assign(N,0);
	_atomForceAlongY.assign(N,0);
	_atomForceAlongZ.assign(N,0);

	for (int i = 0; i < N-1; i++)
	{
		for (int j = i + 1; j < N; j++)
		{
			double r = dis[ i * N + j ];
			int note1 = cluster.GetAtomAtIndex(i).GetNote();
			int note2 = cluster.GetAtomAtIndex(j).GetNote();
			Gupta_AtomParamter parameter = (Gupta_AtomParamter&)ReturnAtomParameter(alloy[note1],alloy[note2]);
			double FMJN = r / parameter.r0 - 1;

			double dFMJV = - parameter.P / parameter.r0 * parameter.A * exp( -parameter.P * FMJN ) * 2;
			double dFMJP = -2 * parameter.q / parameter.r0 * parameter.Xi * parameter.Xi * exp( -2 * parameter.q *FMJN );
			double FK = dFMJV - (PEN[i] + PEN[j]) * dFMJP;

			Atom atomOfI = cluster.GetAtomAtIndex(i);
			AtomPos posOfAtomAtI = atomOfI.GetPos();
			Atom atomOfJ = cluster.GetAtomAtIndex(j);
			AtomPos posOfAtomAtJ = atomOfJ.GetPos();
			_atomForceAlongX[i] = _atomForceAlongX[i]+FK*(posOfAtomAtI.x-posOfAtomAtJ.x)/r;
			_atomForceAlongX[j] = _atomForceAlongX[j]-FK*(posOfAtomAtI.x-posOfAtomAtJ.x)/r;
			_atomForceAlongY[i] = _atomForceAlongY[i]+FK*(posOfAtomAtI.y-posOfAtomAtJ.y)/r;
			_atomForceAlongY[j] = _atomForceAlongY[j]-FK*(posOfAtomAtI.y-posOfAtomAtJ.y)/r;
			_atomForceAlongZ[i] = _atomForceAlongZ[i]+FK*(posOfAtomAtI.z-posOfAtomAtJ.z)/r;
			_atomForceAlongZ[j] = _atomForceAlongZ[j]-FK*(posOfAtomAtI.z-posOfAtomAtJ.z)/r;
		}
	}

	cluster.SetForceXYZVectorOfAtoms(_atomForceAlongX,_atomForceAlongY,_atomForceAlongZ);

	double forceXOfCluster = 0, forceYOfCluster = 0, forceZOfCluster = 0;
	for (int i = 0; i < N; i++)
	{
		forceXOfCluster += _atomForceAlongX[i] * _atomForceAlongX[i];
		forceYOfCluster += _atomForceAlongY[i] * _atomForceAlongY[i];
		forceZOfCluster += _atomForceAlongZ[i] * _atomForceAlongZ[i];
	}

	double F = sqrt(forceXOfCluster  + forceYOfCluster  + forceZOfCluster );
	cluster.SetForceOfCluster(F);

	return F;
}