繁体   English   中英

为什么这个OpenMP计划每次给我不同的答案?

[英]Why is this OpenMP program giving me different answers every time?

我正在尝试使用多个线程运行此程序。

#include <stdio.h>
#include <time.h>
#include <omp.h>

#define NUM_THREADS 4
static long num_steps = 1000000000;

int main()
{
  int i;
  double x, pi, sum = 0.0;
  double step = 1.0/(double)num_steps;

  clock_t start = clock(), diff;
  #pragma omp parallel for num_threads(NUM_THREADS) reduction (+:sum)   
  for (i = 0; i < num_steps; i++)
  {
    x = (i+0.5)*step;
    sum += 4.0/(1.0 + x*x);
  }
  #pragma omp ordered
  pi = step*sum;
  printf("pi = %.15f\n %d iterations\n", pi, num_steps);

  diff = clock() - start;
  int msec = diff * 1000 / CLOCKS_PER_SEC;
  printf("Time taken %d seconds %d milliseconds", msec/1000, msec%1000);

  return 0;
}

通过#pragma omp parallel for num_threads(NUM_THREADS) reduction (+:sum)添加#pragma omp parallel for num_threads(NUM_THREADS) reduction (+:sum) 我也在for循环后#pragma omp ordered ,我认为我实际上并不需要因为在所有线程完成for循环之前没有线程继续。 它是否正确? 这也是我将其作为单线程程序运行而只获得第二次性能提升的原因吗? 这是6秒,而我只有7秒。

我无法回答的是为什么这个程序每次运行时都会给我一个不同的答案?

除了吉尔斯指出的错误之外,这里还有一个更基本的问题。

跨并行线程的减少不一定是确定性的。 每个线程贡献的组合顺序可以随着代码的每次执行而改变。 如果你不知道为什么重要,请去阅读“ 每个计算机科学家应该知道的关于浮点运算的内容

如果你没有得到这一点,但是,考虑三个线程在十进制算术机器上进行总和减少,该机器支持三位精度。 假设我们正在累积集合(100,-100,0.1),如果我们按顺序添加它们,我们将有100 - 100 = 0 + 0.1 = 0.1,但是如果我们按顺序添加它们(100,0.1, - 100),我们将获得100 + 0.1 = 100(三位有效数字,记住!)-100 == 0

如果您正在使用英特尔编译器,则可以设置一个环境变量来请求确定性减少( KMP_DETERMINISTIC_REDUCTION ),但是只有在使用相同数量的线程时才强制执行确定性。 它不会在具有不同线程数的运行之间强制执行它。 (这样做需要强制执行每线程贡献累积的顺序,这将需要不同的代码生成和一些线程间同步)。

您的问题来自于您忘记声明x private的事实。 如果将OpenMP指令更改为:

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

你的代码变得有效。

但是,这里仍有两个问题:

  1. #pragma omp ordered是没有意义的,因为你没有进入parallel区域。 你应该删除它。
  2. 利用clock()在多线程代码的测量时间是危险的,而不是因为函数不是线程安全的,但由于它返回当前线程它的孩子们的,而不是经过时间CPU时间 因此,在使用和未激活OpenMP时,您通常会得到几乎相同的结果,并且人们想知道为什么他们的代码不会暴露任何加速...所以除非您有充分的理由使用clock() ,否则请使用omp_get_wtime()而不是。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM