这样做有什么危害的解决方案?
#include <iostream>
#include <unistd.h>
#include <cstdlib>
#include <ctime>
int main(){
int k = 0;
#pragma omp parallel for
for(int i = 0; i < 100000; i++){
if (i % 2){ /** Conditional based on i **/
#pragma omp atomic
k++;
usleep(1000 * ((float)std::rand() / RAND_MAX));
#pragma omp task
std::cout << k << std::endl; /** Some sort of task **/
}
}
return 0;
}
我需要所有k
都是唯一的。什么是更好的方法呢?
请注意this question如何引用汇总
特别是我想基于共享变量生成任务。我冒着遇到竞争条件的风险。
考虑线程2完成,对条件求值为true,并在线程1产生所有任务之前递增k。
我试图强迫竞争条件。没有睡觉就不明显了。事实上存在问题。我怎么能克服这个。
这是一个快速解决方案:
...
#pragma omp atomic
k++;
int c = k;
...
但我想要保证。
切向。为什么这个实现不起作用?
...
int c;
#pragma omp crtical
{
k++;
c = k;
}
...
在函数结束时,std::cout << k;
始终小于预期的50000输出proof
答案 0 :(得分:1)
我不想这么快回答我的问题,但我找到了这个特定实例的解决方案。
从OpenMP 3.1开始,有"atomic capture" pragma
用例就是针对这样的问题。结果代码:
#include <iostream>
#include <unistd.h>
#include <cstdlib>
#include <ctime>
int main(){
int k = 0;
#pragma omp parallel for
for(int i = 0; i < 100000; i++){
if (i % 2){ /** Conditional based on i **/
int c;
#pragma omp atomic capture
{
c = k;
k++;
}
usleep(1000 * ((float)std::rand() / RAND_MAX));
#pragma omp task
std::cout << c << std::endl; /** Some sort of task **/
}
}
std::cout << k << std::endl; /** Some sort of task **/
std::cout.flush();
return 0;
}
如果有人愿意提供想法/代码拱,我会将此问题保持开放。避免这些问题的建议,#pragma omp crtical
不起作用的原因