OpenMP中数据私有化语句初探 zz

来源:互联网 发布:报销软件 编辑:程序博客网 时间:2024/05/18 03:44

【转】OpenMP中数据私有化语句初探

OpenMP中数据私有化语句初探--private;firstprivate;lastprivate;threadprivate,copyin

         今天晚上考多核程序设计,其中有OpenMP的部分;早上刚刚研究出来以上数据私有化语句的用法,把我的理解贴出来分享了;由于一会儿还要去上课,时间不多,就挑重点的简单说一下了~

         private子句用于将一个或多个变量声明成线程私有的变量,变量声明成私有变量后,指定每个线程都有它自己的变量私有副本,其他线程无法访问私有副本。即使在并行区域外有同名的共享变量,共享变量在并行区域内不起任何作用,并且并行区域内不会操作到外面的共享变量。

         注意:用private子句声明的私有变量在并行区域的入口处是未初始化的,使用之前必须赋初值,否则编译运行时会报错 ;即并行区域内的变量与原同名变量没有任何关系,只是名字相同而已

         实际中常常需要让private子句声明的私有变量继承同名变量的值,这时可以就可以在并行区域的入口处用firstprivate子句,告诉编译器用父线程的值初始化并行区域的子线程中的变量

         类似地,lastprivate子句,如lastprivate(val)用来告诉编译器,把val在最后一个子线程中的值,拷回给父进程

         下面举个例子,说明threadprivate和copyin的基本用法

int global=111;

#pragma omp threadprivate(global)

int _tmain(int argc, _TCHAR* argv[])

{

     global=222;

#pragma omp parallel copyin(global) //

     {

         printf("Thread number %d global=%d\n",omp_get_thread_num(),global);

         global=omp_get_thread_num()+10;      

     }

     printf("global=%d\n",global);

     printf("parallel again\n");

#pragma omp parallel

     printf("Thread number %d global=%d\n",omp_get_thread_num(),global);

     printf("global=%d\n",global);

     return 0;

}

    当环境变量 OMP_NUM_THREADS 设置为4时,运行结果类似于:(知道我为什么说“类似于”吧?各子线程的运行次序不是一定的)

      threadprivate子句用来指定全局的对象被各个线程各自复制了一个私有的拷贝,即各个线程具有各自私有的全局对象。

用法如下:

#pragma omp threadprivate(list) new-line

threadprivate和private的区别在于:threadprivate声明的变量通常是全局范围内有效的,而private声明的变量只在它所属的并行构造中有效。

      copyin子句用来将主线程中threadprivate变量的值拷贝到执行并行区域的各个线程的threadprivate变量中,便于线程可以访问主线程中的变量值,

用法如下:

copyin(list)

copyin中的参数必须被声明成threadprivate的,对于类类型的变量,必须带有明确的拷贝赋值操作符。

    简单分析一下上面的例子:如果去掉copyin语句,则在第一个并行块中,只有主线程(即Thread number=0的线程)中的global的初始值为222,另外三个线程中,其值为全局的111,这就是threadprivate的作用

     上面的并行块执行完之后,三个子进程并没有销毁,而是进入挂起状态

     下面的并行块没有使用copyin子句,这时打印出来的global的值,就是被唤醒的各线程中的值;中间和最后一行的global=10指的都是主线程中的值

原创粉丝点击