C3015:OpenMP 'for'语句中的初始化格式不正确

C3015: initialization in OpenMP 'for' statement has improper form

本文关键字:初始化 不正确 格式 for OpenMP C3015 语句      更新时间:2023-10-16

我有并行扫描算法:Hillis &Steele(1986)和我想要执行内部for循环并行。

Error   C3015   initialization in OpenMP 'for' statement has improper form  OpenMP  c:usersmatjadocumentsvisual studio 2015projectspsseminaropenmpmain.c

我从来没有遇到过这个错误,我已经谷歌了一下,但没有发现任何有用的。

包括:

#include <omp.h>
#include <stdlib.h>
#include <stdio.h>
#include <math.h>
#include <time.h>
#include <limits.h>
#include <windows.h>

代码块:

// ...
for (long long m = 0; m < M; m++)
{
    long long offset = (long long)pow(2, m);
    #pragma omp parallel for firstprivate(N, m, offset)
    for (long long n = offset; n < N; n++)
    {
        long long ai = n - offset;
        long long bi = n;
        // ...
    }
}
// ...

根据MSDN, OP发布的错误是在OpenMP for没有完全明确时引发的。这可能是因为编译器不能完全理解语句

所使用的C99语言。
for (long long n = offset; n < N; n++)

尽管我没有Visual c++编译器,但我看到gcc 4.8.5和icc 16.0.3无法编译它,需要用适当的C99语言变体(即-std=c99)编译代码。在谷歌搜索了一下之后,我还没有找到合适的MSVC标志(事实上,维基百科声称MSVC 2013的支持是有限的(见https://en.wikipedia.org/wiki/C99))。另一种方法是将这段代码转换成

long long m;
for (m = 0; m < M; m++)
{
    long long offset = (long long)pow(2, m);
    long long n;
    #pragma omp parallel for firstprivate(N, m, offset)
    for (n = offset; n < N; n++)
    {
        long long ai = n - offset;
        long long bi = n;
        // ...
    }
}

另外,请注意,如果在并行循环中不进行修改,您可能可以去掉firstprivate子句N, moffset,并将它们更改为shared

BTW,我不同意tahini的回答,他们声称#pragma omp parallel for仅限于intunsigned int,因为下面的代码在gcc 4.8.5和icc 16.0.3中都可以完美地工作。

#include <omp.h>
#include <stdio.h>
void main (void)
{
    long long m;
    #pragma omp parallel for schedule
    for (m = 0; m < 16; m++)
    {
            printf ("thread = %d, m = %dn", omp_get_thread_num(), m);
    }
}

对于的omp并行中的迭代变量被限制为int型或unsigned int型。long类型的long不是一个有效的迭代器类型。

https://computing.llnl.gov/tutorials/openMP/ParallelRegion