我看过官方的定义,但我仍然很困惑.
firstprivate:指定每个线程应该有自己的变量实例,并且应该使用变量的值初始化变量,因为它存在于并行构造之前.
对我来说,这听起来很像私人.我找了一些例子,但我似乎不明白它的特殊性或如何使用它.
lastprivate:指定将封闭上下文的变量版本设置为等于执行最终迭代(for-loop构造)或最后一个部分(#pragma sections)的任何线程的私有版本.
由于以下示例,我觉得我更了解这一点:
#pragma omp parallel
{
#pragma omp for lastprivate(i)
for (i=0; i<n-1; i++)
a[i] = b[i] + b[i+1];
}
a[i]=b[i];
Run Code Online (Sandbox Code Playgroud)
所以,在这个例子中,我理解lastprivate允许i在循环之外作为最后一个值返回.
我今天刚开始学习OpenMP.
Hri*_*iev 134
private变量没有初始化,即它们像任何其他本地自动变量一样以随机值开始(并且它们通常使用每个线程的堆栈上的自动变量来实现).以这个简单的程序为例:
#include <stdio.h>
#include <omp.h>
int main (void)
{
int i = 10;
#pragma omp parallel private(i)
{
printf("thread %d: i = %d\n", omp_get_thread_num(), i);
i = 1000 + omp_get_thread_num();
}
printf("i = %d\n", i);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
有四个线程,它输出如下:
thread 0: i = 0
thread 3: i = 32717
thread 1: i = 32717
thread 2: i = 1
i = 10
(another run of the same program)
thread 2: i = 1
thread 1: i = 1
thread 0: i = 0
thread 3: i = 32657
i = 10
Run Code Online (Sandbox Code Playgroud)
这清楚地表明,i并行区域内的值是随机的(未初始化的),并且在并行区域之后对其进行的任何修改都是不可见的(即变量在进入区域之前保持其值).
如果i制成firstprivate,那么它被初始化与它具有平行区域之前的值:
thread 2: i = 10
thread 0: i = 10
thread 3: i = 10
thread 1: i = 10
i = 10
Run Code Online (Sandbox Code Playgroud)
i之后对平行区域内部值的修改仍然不可见.
您已经了解lastprivate(并且它不适用于简单的演示程序,因为它缺少工作共享结构).
所以是的,firstprivate而且lastprivate只是特殊情况private.第一个导致将值从外部上下文引入并行区域,而第二个将值从并行区域传输到外部上下文.这些数据共享类背后的基本原理是,在并行区域内,所有私有变量都会遮蔽来自外部上下文的私有变量,即不可能使用赋值操作来修改i并行区域内部的外部值.
| 归档时间: |
|
| 查看次数: |
45543 次 |
| 最近记录: |