我正在开发一个程序,该程序使用多个线程来计算一定数量的素数。现在我遇到了在上述数目的素数之后退出线程的问题。
我已经尝试过#pragma omp cancel for
,但是不能在有序子句中使用它。还有另一种“打破”循环的方法吗?
void get_primes(prime_type start, prime_type end) {
#pragma omp parallel for ordered schedule(dynamic) shared(prime_counter)
for (candidate = start; candidate <= end; candidate += 2) {
if (is_prime(candidate)) {
#pragma omp ordered
{
primes[prime_counter] = candidate;
prime_counter++;
if (prime_counter >= max_primes) {
#pragma omp cancel for
}
#pragma omp cancellation point for
}
}
}
}
当我发现所需的素数时,我想立即“打破”循环,如果我没有记错的话,那必须在有序子句中完成。
答案 0 :(得分:1)
不。无法取消有序循环。
被取消的循环结构不能具有有序子句。
(参见OpenMP标准2.14.1)
模拟取消的一种解决方法是在循环开始时添加一个跳过,例如
#pragma omp parallel for ordered schedule(dynamic) shared(prime_counter)
for (candidate = start; candidate <= end; candidate += 2) {
if (prime_counter >= max_primes) {
continue;
}
if (is_prime(candidate)) {
但是,这还不是线程安全访问prime_counter
的权限。为了避免出现竞赛情况,您必须按照以下步骤进行操作:
int local_prime_counter;
#pragma omp atomic read
local_prime_counter = prime_counter;
if (local_prime_counter >= max_primes)
...
#pragma omp atomic update
prime_counter++;
P.S。我不确定100%确定是否有条件ordered
构造是否符合标准。