我正在尝试使用openMP迭代c ++中的地图,但是我收到三条错误消息,说明了 我的循环的初始化,终止和增量有不正确的形式,我在使用openmp时很新,所以有没有办法解决这个问题,同时得到与串行结果相同的结果?以下是我使用的代码
map< int,string >::iterator datIt;
#pragma omp parallel for
for(datIt=dat.begin();datIt!=dat.end();datIt++) //construct the distance matrix
{
...............
}
答案 0 :(得分:3)
也可以通过使用基于带有std::advance
的循环球杆的简单索引来到达特定的地图元素。 OpenMP 2.0非常支持基于索引的循环。
#pragma omp parallel for
for(int i = 0; i < dat.size(); i++) {
auto datIt = dat.begin();
advance(datIt, i);
//construct the distance matrix using iterator datIt
}
在每个线程中,迭代器datIt
将指向一个map项,并可用于对其执行操作。
答案 1 :(得分:2)
您的OpenMP实现可能与STL迭代器不兼容。虽然有一些changes to the standard to make OMP more compatible with the STL,但我认为你会发现你的实现不支持这种行为。我遇到的大多数OpenMP实现最多是2.5版,Microsoft C ++是2.0版。我所知道的唯一支持3.0的编译器是Intel C ++编译器。
其他几点,您应该使用std :: begin和std :: end。此外,您需要将循环不变声明为私有,或者将OpenMP数据单独声明,如下所示:
#pragma omp parallel for
for(map< int,string >::iterator datIt = std::begin(dat);
datIt != std::end(dat);
datIt++)
{
//construct the distance matrix...
}
但是没有3.0的支持,这就不合时宜了。
答案 2 :(得分:0)
现在可以在gcc上使用OpenMP 3.0,英特尔编译器有任务指令,允许线程将任务委托给线程拉
受到启发:this response和this course,我写了这些适用于我的代码:
map< int,string >::iterator datIt;
...
#pragma omp parallel for
#pragma omp single nowait
{
for(datIt=dat.begin();datIt!=dat.end();datIt++) //construct the distance matrix
{
#pragma omp task firstprivate(datIt)
{
...............
}
}
}
一个任务(单个指令)遍历整个地图,并将地图中每个元素的每个任务都放到一系列任务中。其他OMP线程处理任务仍然存在。其他OMP任务没有必要等待 for 循环结束以启动任务处理( nowait )。每个任务都有一个要处理的地图元素指针( firstprivate(datIt))。
约束:每个任务必须是独立的,并且地图在结束之前不能改变。
答案 3 :(得分:-1)
如果它有用,请尝试这种方式。
#pragma omp parallel for shared(dat) private(datIt)
for(map< int,string >::iterator datIt=dat.begin();datIt!=dat.end();datIt++)
{
...............
}