Openmp omp并行与omp并行
这两者有什么区别 [A]Openmp omp并行与omp并行,openmp,Openmp,这两者有什么区别 [A] #pragma omp并行 { #pragma omp for 对于(int i=1;i
#pragma omp并行
{
#pragma omp for
对于(int i=1;i<100;++i)
{
...
}
}
[乙]
#pragma omp parallel for
对于(int i=1;i<100;++i)
{
...
}
我不认为有什么区别,一个是另一个的捷径。尽管您的具体实现可能会以不同的方式处理它们
组合的并行工作共享构件是
指定包含一个工作共享构件的并行构件
没有其他声明。允许条款是这些条款的结合
允许并行和工作共享施工
取自
OpenMP的规格如下所示:
这些是等效的
#pragma omp parallel
生成一组线程,而#pragma omp for
在生成的线程之间划分循环迭代。您可以使用fused#pragma omp parallel for
指令同时完成这两件事。在g++4.7.0中使用for循环时,我看到了截然不同的运行时
和使用
std::vector<double> x;
std::vector<double> y;
std::vector<double> prod;
for (int i = 0; i < 5000000; i++)
{
double r1 = ((double)rand() / double(RAND_MAX)) * 5;
double r2 = ((double)rand() / double(RAND_MAX)) * 5;
x.push_back(r1);
y.push_back(r2);
}
int sz = x.size();
#pragma omp parallel for
for (int i = 0; i< sz; i++)
prod[i] = x[i] * y[i];
std::向量x;
std::向量y;
std::向量prod;
对于(int i=0;i<5000000;i++)
{
double r1=((双)rand()/double(rand_MAX))*5;
双r2=((双)兰德()/双(兰德最大值))*5;
x、 推回(r1);
y、 推回(r2);
}
int sz=x.size();
#pragma-omp并行
对于(int i=0;i
串行代码(无openmp
)运行79毫秒。
“parallel for”代码运行时间为29毫秒。
如果我省略的,并使用#pragma omp parallel
,则运行时将达到179ms,
这比串行代码慢。(机器的hw并发性为8)
代码链接到libgomp
,这里是使用分离的并行
和的示例。简而言之,它可以用于在多个线程中执行for
cycle之前动态分配OpenMP线程专用阵列。
对于
情况,不可能在并行中执行相同的初始化
UPD:
在问题示例中,单个pragma和两个pragma之间没有区别。但在实践中,您可以使用分离的并行和for指令来实现更多的线程感知行为。
一些代码,例如:
#pragma omp parallel
{
double *data = (double*)malloc(...); // this data is thread private
#pragma omp for
for(1...100) // first parallelized cycle
{
}
#pragma omp single
{} // make some single thread processing
#pragma omp for // second parallelized cycle
for(1...100)
{
}
#pragma omp single
{} // make some single thread processing again
free(data); // free thread private data
}
尽管具体示例的两个版本是等效的,正如其他答案中已经提到的,但它们之间仍然有一个小的区别。第一个版本包括“omp for”结尾处遇到的不必要的隐式障碍。另一个隐式势垒位于平行区域的末端。至少从OpenMP的角度来看,将“nowait”添加到“omp for”将使这两个代码等效。我之所以提到这一点,是因为OpenMP编译器可以为这两种情况生成稍有不同的代码。显然有很多答案,但这一个答案很好地解决了这一问题(源代码)
#pragma omp for
仅为
当前团队中的不同线程。团队是线程组
执行程序。在项目开始时,团队仅由一名
单个成员:运行程序的主线程
要创建新的线程组,需要指定并行线程
关键词。可以在周围的上下文中指定:
#pragma omp parallel
{
#pragma omp for
for(int n = 0; n < 10; ++n)
printf(" %d", n);
}
#pragma omp并行
{
#pragma omp for
对于(int n=0;n<10;++n)
printf(“%d”,n);
}
以及:
什么是:平行,为和一个团队
平行线之间的区别,
与之平行的如下所示:
团队是一组线程
当前正在执行的。在项目开始时,团队由以下人员组成:
一根线。并行构造将当前线程拆分为
下一个块/语句期间的新线程组,
之后,团队合并为一个团队。因为他把工作分成两部分
在当前团队的线程之间进行for循环
它不会创建
线程,它只在当前
执行团队。parallel for是同时表示两个命令的缩写:
平行和平行。Parallel创建了一个新团队,对于拆分
团队负责处理循环的不同部分。如果你的程序从来没有
包含一个并行构造,没有多个线程;
启动并运行程序的主线程,如中所示
非线程程序
TL;DR:唯一的区别是第一个代码调用两个隐式屏障,而第二个代码只调用一个
参考官方OpenMP 5.1标准的更详细答案。
#pragma omp parallel
:
将创建一个并行区域
,其中包含一组线程
,每个线程将执行并行区域
包含的整个代码块
从中可以看到更正式的描述:
当一个线程遇到一个并行构造时,一个线程组被激活
创建以执行并行区域(..)。这个
遇到并行构造的线程成为主线程
新团队的线程,在持续时间内线程数为零
新的平行区域新团队中的所有线程,包括
主线程,执行区域。创建团队后
团队中的线程数在任务期间保持不变
平行区域
委员会:
#pragma omp parallel for
将创建一个并行区域
(如前所述),并将使用默认块大小
和默认调度
(通常为静态
)为该区域的线程
分配它所包含的循环迭代。忍受
#pragma omp parallel
{
double *data = (double*)malloc(...); // this data is thread private
#pragma omp for
for(1...100) // first parallelized cycle
{
}
#pragma omp single
{} // make some single thread processing
#pragma omp for // second parallelized cycle
for(1...100)
{
}
#pragma omp single
{} // make some single thread processing again
free(data); // free thread private data
}
#pragma omp parallel
{
#pragma omp for
for(int n = 0; n < 10; ++n)
printf(" %d", n);
}
for(int i=omp_get_thread_num(); i < n; i+=omp_get_num_threads())
{
//...
}