计数在 OpenMP 中无法正常工作
Counting does not work properly in OpenMP
我有这个功能
void collatz(int startNumber, int endNumber, int* iter, int nThreads)
{
int i, n, counter;
int isodd; /* 1 if n is odd, 0 if even */
#pragma omp parallel for
for (i = startNumber; i <= endNumber; i++)
{
counter = 0;
n = i;
omp_set_num_threads(nThreads);
while (n > 1)
{
isodd = n%2;
if (isodd)
n = 3*n+1;
else
n/=2;
counter++;
}
iter[i - startNumber] = counter;
}
}
它在 运行 串行时如我所愿地工作(即在没有 OpenMP 的情况下编译或注释掉 #pragma omp parallel for
和 omp_set_num_threads(nThreads);
)。然而,并行版本产生了错误的结果,我认为这是因为 counter
变量需要在每个 for 循环开始时设置为零,也许另一个线程可以使用非零 counter
价值。但是即使我使用#pragma omp parallel for private(counter)
,问题仍然存在。我错过了什么?
我把程序编译成C89。
在您的 OpenMP 并行区域中,您正在为 counter
、n
和 isodd
标量变量赋值。因此,它们不能像默认情况下那样只是 shared
。你需要格外注意它们。
快速分析表明,由于它们的值仅在并行区域内且仅对当前线程有意义,因此很明显需要声明它们 private
。
在 #pragma omp parallel
指令中添加 private( counter, n, isodd )
子句应该可以解决问题。
我有这个功能
void collatz(int startNumber, int endNumber, int* iter, int nThreads)
{
int i, n, counter;
int isodd; /* 1 if n is odd, 0 if even */
#pragma omp parallel for
for (i = startNumber; i <= endNumber; i++)
{
counter = 0;
n = i;
omp_set_num_threads(nThreads);
while (n > 1)
{
isodd = n%2;
if (isodd)
n = 3*n+1;
else
n/=2;
counter++;
}
iter[i - startNumber] = counter;
}
}
它在 运行 串行时如我所愿地工作(即在没有 OpenMP 的情况下编译或注释掉 #pragma omp parallel for
和 omp_set_num_threads(nThreads);
)。然而,并行版本产生了错误的结果,我认为这是因为 counter
变量需要在每个 for 循环开始时设置为零,也许另一个线程可以使用非零 counter
价值。但是即使我使用#pragma omp parallel for private(counter)
,问题仍然存在。我错过了什么?
我把程序编译成C89。
在您的 OpenMP 并行区域中,您正在为 counter
、n
和 isodd
标量变量赋值。因此,它们不能像默认情况下那样只是 shared
。你需要格外注意它们。
快速分析表明,由于它们的值仅在并行区域内且仅对当前线程有意义,因此很明显需要声明它们 private
。
在 #pragma omp parallel
指令中添加 private( counter, n, isodd )
子句应该可以解决问题。