gpt4 book ai didi

C++ OpenMP for循环全局变量问题

转载 作者:太空宇宙 更新时间:2023-11-04 12:01:12 29 4
gpt4 key购买 nike

我是 OpenMP 的新手,从我读到的有关 OpenMP 2.0(Microsoft Visual Studio 2010 的标准配置)的内容来看,在并行编程中使用全局变量被认为是麻烦且容易出错的。我也一直有这种感觉,因为我发现很少关于如何有效地处理全局变量和静态全局变量,或者根本没有发现。

我有这段代码在运行,但由于在并行 block 中创建的局部变量,我没有得到我正在寻找的答案。我得到 8 个不同的打印输出(因为我的 PC 上有多少个线程)而不是 1 个答案。我知道这是因为在并行 block 中创建了局部变量“list”,但如果我移动“list”变量并将其设为全局变量,则此代码将不会运行。实际上代码确实运行了,但它从来没有给我回复。这是我想修改为使用全局“列表”变量的示例代码:

#pragma omp parallel
{
vector<int> list;
#pragma omp for
for(int i = 0; i < 50000; i++)
{
list.push_back(i);
}
cout << list.size() << endl;
}

输出:

6250
6250
6250
6250
6250
6250
6250
6250

他们加起来是 50000,但我没有得到 50000 的答案,而是将其分开。

解决方法:

    vector<int> list;
#pragma omp parallel
{
#pragma omp for
for(int i = 0; i < 50000; i++)
{
cout << i << endl;
#pragma omp critical
{
list.push_back(i);
}
}
}
cout << list.size() << endl;

最佳答案

根据MSDN Documentation平行从句

Defines a parallel region, which is code that will be executed by multiple threads in parallel.

并且由于列表变量是在本节中声明的,所以每个线程都有自己的列表。

另一方面,for pragma

Causes the work done in a for loop inside a parallel region to be divided among threads.

所以 50000 次迭代将在线程之间拆分,但每个线程都有自己的列表。我认为你正在尝试做的事情可以通过以下方式实现:

  1. 将列表定义放在“并行”部分之外。
  2. critical section 保护 list.push_back 语句.

试试这个:

vector<int> list;
#pragma omp parallel
{
#pragma omp for
for(int i = 0; i < 50000; i++)
{
#pragma omp critical
{
list.push_back(i);
}
}
}
cout << list.size() << endl;

在这种情况下,我认为您不应该从 OpenMP 获得任何加速,因为将存在对关键部分的争用。一个更快的解决方案(如果你不关心元素的顺序)是让每个线程都有自己的列表,并在循环完成后合并这些列表。在这种情况下,使用 std::list 而不是 std::vector 的实现看起来会更干净(因为您不必复制数组)。

有些应用受内存限制而不是计算限制。底线:检查您是否真的从 OpenMP 获得了加速。

关于C++ OpenMP for循环全局变量问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14035729/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com