如何使用在openMP中保护数组中的一个元素?

时间:2015-04-11 08:06:01

标签: c parallel-processing openmp

例如:

int a[100];
int i=0;
for(i=0;i<100;i++)
{
   a[i]=i;
}
#pragma omp parallel for firstprivate(a[0])
for(i=0;i<100;i++)
{

    a[i]=a[i]+a[((i+1)%100)];

}

然而,它编译失败:

error: syntax error in omp clause
 #pragma omp parallel for firstprivate(a[0])
                                        ^

对不起我以前的描述。我希望输出为:a [i] = a [i] + a [((i + 1)%100)],例如,a [10] = a [10] + a [11],a [ 99] = A [99] + A [0]。但是,当我变成99时,[99]应该是[99] = a [99] + a [0]。但是当线程执行[99] = a [99] + a [0]时,a [0]的值已被另一个并行线程变为[0] = a [0] + a [1](它有依赖)。我该怎么做才能保证每个线程都能在[i]中使用原始值来完成[i] = a [i] + a [((i + 1)%100)]?

1 个答案:

答案 0 :(得分:2)

您的代码无法保证获得正确的结果,因为它具有竞争条件。解决这个问题的一种方法是像这样

这样做
void foo2(int * __restrict a, int * __restrict b) {
    int i;
    #pragma omp parallel for schedule(static)
    for (i = 0; i<N; i++) {
        b[i] = a[i] + a[((i + 1) % N)];
    }   
}

如果你真的想在现场进行,那就有点复杂了

void foo3(int a[]) {    
    int n = N - 1;
    #pragma omp parallel
    {
        int i;
        int ithread = omp_get_thread_num();
        int nthread = omp_get_num_threads();
        int start = ithread*n / nthread;
        int finish = (ithread + 1)*n/ nthread;
        int tmp = a[finish];
        for (i = start; i < finish-1; i++) {
            a[i] += a[i + 1];
        }
        a[finish-1] += tmp;
    }
    a[n] += a[0];
}