我在下面的函数并行化时遇到了错误。
bool
CMolecule::computeForces_twobody(vector<CMolecule*> &mols,
vector<CPnt> & force, vector<CPnt> & torque)
{
if(mols.size() == 1 ) return true;
int nmol=mols.size();
int M2=nmol*(nmol-1)/2;
vector<CMolecule*> twomols;
vector<CPnt> force2b(nmol),torque2b(nmol);
vector<CSphereIDPair> dimer;
CPnt forcetemp,torquetemp;
for(int i=0;i<nmol;i++)
for(int j=i+1;j<nmol;j++)
{
dimer.push_back(CSphereIDPair(i,j));
}
#pragma omp parallel for private(twomols, forcetemp, torquetemp)
for(int i=0;i<M2;i++)
{
twomols.push_back(new CMolecule(*mols[dimer[i].is]));
twomols.push_back(new CMolecule(*mols[dimer[i].js]));
bool bInterXFS = CMolecule::generateInterXFormsForPolarize_LowMemory(twomols);
if(! bInterXFS )
cout <<"error in generateInterXFormsForPolarize_LowMemory"<<endl;
CMolecule::polarize_mutual(twomols,false, 1000);
twomols[0]->computeMol_Force_and_Torque(forcetemp,torquetemp);
force2b[dimer[i].is]+=forcetemp;
torque2b[dimer[i].is]+=torquetemp;
twomols[1]->computeMol_Force_and_Torque(forcetemp,torquetemp);
force2b[dimer[i].js]+=forcetemp;
torque2b[dimer[i].js]+=torquetemp;
twomols.clear();
}
for(int i=0;i<nmol;i++)
{
force[i]=force2b[i];
torque[i]=torque2b[i];
}
return true;
}
串口代码可以正常运行。但是,当并行运行时,程序在函数'polarize_mutual'崩溃并生成核心转储文件(遗憾的是我没有从核心转储文件中找到任何有用的信息)。所以我怀疑我的复制操作可能有问题。
twomols.push_back(new CMolecule(*mols[dimer[i].is]));
twomols.push_back(new CMolecule(*mols[dimer[i].js]));
我没有看到任何错误,但我怀疑这个复制操作可能是一个浅拷贝。这是因为类'CMolecule'的对象是使用包含许多指针的构造函数构造的。
CMolecule::CMolecule(int moltype, CPnt rcen, const vector<CPnt> &cens, const vector<double> &radii,
const vector<double> &chg, const vector<CPnt> &cpos, double idiel,
const vector<REAL*> &iMats, REAL intraRcutoff,
const vector<vector<CPnt> > &SPxes, const vector<int> &nSPx,
const vector<vector<int> >&neighs,
const vector< vector<int> > &intraPolLists_near,
const vector<CMulExpan*> &Fself, const vector<CMulExpan*> &Hself,
const vector<CLocalExpan*> & LFs_intraSelf, const vector<CLocalExpan*> &LHs_intraSelf,
const vector<CLocalExpan*> & LFs_intraSelf_far, const vector<CLocalExpan*> &LHs_intraSelf_far,
const vector<vector<REAL> > &qSolvedFself,
const vector<vector<REAL> > &qSolvedHself,
const vector<double> &totalFself, const vector<double> &totalHself,
const vector<CMolCell> &molcell)
: m_rot(false), m_p(N_POLES), m_idiel(idiel), m_bKappa(false), m_bAggregateM(false), m_moltype(moltype),
m_molcells(molcell)
是否有必要为类'CMolecule'编写复制构造函数来执行深层复制?
答案 0 :(得分:0)
你真的需要twomols STL向量来保存对2个CMolecule的引用吗?您的实现似乎非常浪费CPU周期。我想这些内容可能更容易让编译器进行优化:
#pragma omp parallel for private(twomols, forcetemp, torquetemp)
for(int i=0;i<M2;i++)
{
const CMolecule& a = mols[dimer[i].is];
const CMolecule& b = mols[dimer[i].js];
CMolecule::polarize_mutual(a, b, false, 1000);
// (...)
}