如何将 for 循环转换为 STL for_each 语句

发布于 2024-08-24 06:45:02 字数 522 浏览 1 评论 0原文

我想将 for 循环转换为 STL std::for_each 循环。

 bool CMyclass::SomeMember()
 {
    int ii;
        for(int i=0;i<iR20;i++)
            {
              ii=indexR[i];
              ishell=static_cast<int>(R[ii]/xStep);
              theta=atan2(data->pPOS[ii*3+1], data->pPOS[ii*3]);
              al2[ishell] += massp*cos(fm*theta);
            }
 }

实际上,我计划使用 g++4.4 中的并行 STL,

 g++ -D_GLIBCXX_PARALLEL -fopenmp

如果代码是用标准 STL 库编写的,则允许并行运行代码而无需更改。

I would like to convert my for loop to STL std::for_each loop.

 bool CMyclass::SomeMember()
 {
    int ii;
        for(int i=0;i<iR20;i++)
            {
              ii=indexR[i];
              ishell=static_cast<int>(R[ii]/xStep);
              theta=atan2(data->pPOS[ii*3+1], data->pPOS[ii*3]);
              al2[ishell] += massp*cos(fm*theta);
            }
 }

Actually I was planning to use parallel STL from g++4.4

 g++ -D_GLIBCXX_PARALLEL -fopenmp

which is allow to run code in parallel without changes if the code is written in standard STL library.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

我三岁 2024-08-31 06:45:02

您需要将循环体分离成单独的函数或函子;我假设所有未声明的变量都是成员变量。

void CMyclass::LoopFunc(int ii)  {
    ishell=static_cast<int>(R[ii]/xStep);
    theta=atan2(data->pPOS[ii*3+1],
    data->pPOS[ii*3]);
    al2[ishell] += massp*cos(fm*theta);
}

bool CMyclass::SomeMember()  { 
    std::for_each(&indexR[0],&indexR[iR20],std::tr1::bind(&CMyclass::LoopFunc,std::tr1::ref(*this));
}

You need to seperate out the loop body into a seperate function or functor; I've assumed all the undeclared variables are member variables.

void CMyclass::LoopFunc(int ii)  {
    ishell=static_cast<int>(R[ii]/xStep);
    theta=atan2(data->pPOS[ii*3+1],
    data->pPOS[ii*3]);
    al2[ishell] += massp*cos(fm*theta);
}

bool CMyclass::SomeMember()  { 
    std::for_each(&indexR[0],&indexR[iR20],std::tr1::bind(&CMyclass::LoopFunc,std::tr1::ref(*this));
}
安人多梦 2024-08-31 06:45:02
class F {
   public:
   void operator()(int ii) {
              ishell=static_cast<int>(R[ii]/xStep);
              theta=atan2(data->pPOS[ii*3+1], data->pPOS[ii*3]);
              al2[ishell] += massp*cos(fm*theta);
   } 
   F(int[] r): //and other parameters should also be passed into the constructor
      r_(r) {}
   void:
   int[] r_; // refers to R[ii] array
   // and other parameters should also be stored
};

F f(R); // pass other parameters too  
for_each(&indexR[0], &indexR[iR20], f);

然而,使用这种“自动并行化”可能不是一个好主意,因为您需要记住每个并行计算的粒度——我不确定编译器如何很好地考虑粒度大小。

class F {
   public:
   void operator()(int ii) {
              ishell=static_cast<int>(R[ii]/xStep);
              theta=atan2(data->pPOS[ii*3+1], data->pPOS[ii*3]);
              al2[ishell] += massp*cos(fm*theta);
   } 
   F(int[] r): //and other parameters should also be passed into the constructor
      r_(r) {}
   void:
   int[] r_; // refers to R[ii] array
   // and other parameters should also be stored
};

F f(R); // pass other parameters too  
for_each(&indexR[0], &indexR[iR20], f);

However it might not be a good idea to use this "automatic parallelization" since you need to keep in mind the grainsize of each parallel computation -- I am not sure how well the compiler takes the grain size into account.

眼趣 2024-08-31 06:45:02

您不能只是将循环体分离为函子并假设它将被并行化,因为循环体内有太多依赖项。
仅当没有全局数组或指针时,Cycle 才能并行运行。如果你提供完整的功能体那么我们可以考虑如何将其更改为并行版本。

You cannot just separate cycle body into functor and assume that it will be paralellised because you have too many dependencies inside cycle body.
Cycle will be able to run in parallel only if you have no global arrays or pointers. If you provide full function body then we can think how to change it to parallel version.

梦醒灬来后我 2024-08-31 06:45:02

您需要将循环体转换为函数或函子。那里有很多未声明的变量,所以我无法轻易说出如何分离出循环体。这是一个尝试:

class DoStuff
{
  int* R;
  int xStep;
  Data* data;
  double massp;
  double fm;
  double* al2;
public:
  DoStuff(int* R_, int xStep_, Data* data_, double massp_, double fm_, double* al2_) :
    R(R_), xStep(xStep_), data(data_), massp(massp_), fm(fm_), al2(al2_) {}

  void operator()(int ii)
  {
     int ishell = static_cast<int>(R[ii]/xStep);
     double theta = atan2(data->pPOS[ii*3+1], data->pPOS[ii*3]);
     al2[ishell] += massp*cos(fm*theta);
  }
};

for_each(indexR, indexR+iR20, DoStuff(R, xStep, data, massp, fm, al2));

You'll need to convert the loop body into a function or functor. There are a lot of undeclared variables in there, so I can't easily tell how to separate out the loop body. Here's a stab at it:

class DoStuff
{
  int* R;
  int xStep;
  Data* data;
  double massp;
  double fm;
  double* al2;
public:
  DoStuff(int* R_, int xStep_, Data* data_, double massp_, double fm_, double* al2_) :
    R(R_), xStep(xStep_), data(data_), massp(massp_), fm(fm_), al2(al2_) {}

  void operator()(int ii)
  {
     int ishell = static_cast<int>(R[ii]/xStep);
     double theta = atan2(data->pPOS[ii*3+1], data->pPOS[ii*3]);
     al2[ishell] += massp*cos(fm*theta);
  }
};

for_each(indexR, indexR+iR20, DoStuff(R, xStep, data, massp, fm, al2));
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文