【发布时间】:2019-11-08 22:01:48
【问题描述】:
关于 OpenMP 并行化的问题。我在下面包含了我的函数的精简版本。问题是,for 循环的内容并未针对 uiIndex 的所有值进行评估,尽管并非总是如此。
- 我使用缓冲区 vec_succ_status 检查是否所有的 uiIndex 值都得到了评估。事实证明不是。
- 我的代码没有崩溃,它只是从函数 compute_Lagr_shortest_paths_from_source 中退出,没有遇到下面函数定义中的任何 exit(-1) 语句。
- 我在 Ubunutu 14 上使用 g++ 7.4.0 版本,每次失败时,都会跳过一个 uiIndex 值。函数无法评估的 uiIndex 没有一致性。
- 对于我一直在测试的程序,vec_group 的大小始终为 1,因此只有 for 循环中的第一个 if 语句会计算。
- 在我的主函数中,我包含了 omp_set_num_threads(4) 行。除此之外,我没有为 OpenMP 设置任何其他设置(例如调度程序类型)。
- 另外,我可以保证没有 2 个 uiIndex 值会导致相同的 uiRobot 值,因此不会有 2 个线程必须在函数的有效期内访问相同的 vec_cf_graphs[uiRobot] 数组。
我想知道我是否对 OpenMp 做出了一些错误的假设。我要求在所有线程之间共享所有对象,例如 vec_cf_graphs、vec_succ_status。我想知道是否需要明确提及它们是共享的,因为它通常是推荐的方法。无论如何,我认为我实施的方式也足够了。但是,对我来说,某些 uiIndex 值可以完全跳过,这似乎很奇怪。我必须指出,我反复调用显示的函数,但只是有时某些 uiIndex 值会从评估中跳过。如果有人可以指出我的方法的潜在问题,那就太好了。我很高兴提供更多信息。谢谢。
bool compute_Lagr_shortest_paths_from_source(std::vector<Robot_CF_Graph>& vec_cf_graphs, const std::vector<std::vector<size_t>>& vec_robot_groups)
{
size_t uiIndex;
std::vector<bool> vec_succ_status(vec_robot_groups.size(), false);
#pragma omp parallel for default(shared) private(uiIndex)
for(uiIndex = 0; uiIndex < vec_robot_groups.size(); uiIndex++)
{
vec_succ_status[uiIndex] = false;
const auto& vec_group = vec_robot_groups[uiIndex];
if(1 == vec_group.size())
{
size_t uiRobot = vec_group[0];
vec_cf_graphs[uiRobot].compute_shortest_path("ABC");
vec_succ_status[uiIndex] = true;
}
else
{
std::cout<< "Tag: Code should not have entered this block"<<endl;
exit(-1);
}
if(false == vec_succ_status[uiIndex])
{
std::cout<< "It is not possible for this to happen \n";
exit(-1);
}
}
return true;
}
【问题讨论】:
-
也许还值得一提的是,
exit(-1)应该在parallel for构造中被避免。我很惊讶编译器没有警告你,因为我记得如果你使用return,它甚至无法编译。