【问题标题】:Parallel program using openMP使用 openMP 的并行程序
【发布时间】:2014-10-15 12:32:43
【问题描述】:

我正在尝试使用 openMP 使用多线程计算 4/(1+x^2) 在 c++ 中从 0 到 1 的积分。 我拿了一个串行程序(这是正确的)并对其进行了更改。 我的想法是: 假设 X 是线程数。 将函数下方的区域划分为 X 部分,首先从 0 到 1/X,从 1/X 到 2/X... 每个线程都会计算它的面积,我会总结一下。

我是这样实现的:

`//N.o. of threads to do the task
cout<<"Enter num of threads"<<endl;
int num_threads;
cin>>num_threads;

int i; double x,pi,sum=0.0;
step=1.0/(double)num_steps;
int steps_for_thread=num_steps/num_threads;
cout<<"Steps for thread : "<<steps_for_thread<<endl;

//Split to threads
omp_set_num_threads(num_threads);
#pragma omp parallel
{
    int thread_id = omp_get_thread_num();
    thread_id++;

    if (thread_id == 1) 
    {
        double sum1=0.0;
        double x1;
        for(i=0;i<num_steps/num_threads;i++)
        {
            x1=(i+0.5)*step;
            sum1 = sum1+4.0/(1.0+x1*x1);
        }
        sum+=sum1;
    }
    else 
    {
        double sum2=0.0;
        double x2;
        for(i=num_steps/thread_id;i<num_steps/(num_threads-thread_id+1);i++)
        {
            x2=(i+0.5)*step;
            sum2 = sum2+4.0/(1.0+x2*x2);
        }
        sum+=sum2;
    }
} '

说明: 第 i 个线程将计算 i/n 到 (i+1)/n 之间的面积并将其添加到总和中。

问题不仅在于输出错误,而且每次运行程序我得到不同的输出。

欢迎任何帮助 谢谢

【问题讨论】:

  • 添加一些打印语句。
  • 你得到了哪些输出?
  • 取决于线程数。对于 2,我得到 3.6,3.8,2.9,而正确答案是 pi

标签: c++ multithreading openmp


【解决方案1】:

你让这个问题变得比它需要的更难。 OpenMP 的目标之一是不必更改您的串行代码。您通常只需要添加一些 pragma 语句。所以你应该先写串行方法。

#include <stdio.h>    
double pi(int n) {
        int i;
        double dx, sum, x;
        dx = 1.0/n;
        #pragma omp parallel for reduction(+:sum) private(x)
        for(i=0; i<n; i++) {
                x = i*dx;
                sum += 1.0/(1+x*x);
        }
        sum *= 4.0/n;
        return sum;
}
int main(void) {
        printf("%f\n",pi(100000000));
}

输出:3.141593

请注意,在函数pi 中,串行代码和并行版本之间的唯一区别是语句

#pragma omp parallel for reduction(+:sum) private(x)

您通常也不应该担心设置线程数。

【讨论】:

  • @HighPerformanceMark,谢谢,但我刚刚意识到这是一个 C++ 问题,而不是 C。我可以用 C++ 稍微简化一下。令人讨厌的是,出于某种原因,人们认为循环初始声明不适用于 OpenMP 和 C++。我看到 for(i=0; 并认为这是一个 C89 问题。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2022-01-10
  • 2011-01-02
  • 2021-05-10
  • 2016-04-17
  • 2011-01-05
  • 2011-12-29
  • 1970-01-01
相关资源
最近更新 更多