使用任务使用 OpenMP 拆分动态变化的链表

Splitting up a dynamically changing linked list with OpenMP using tasks

我有一个理论上的 OpenMP 问题要问大家。 假设我执行以下操作:

 #pragma omp parallel
 {
    #pragma omp single
    {
    while (!empty(linkedList)) {
      #pragma omp task
              doWork();
      }
    }
 }

如果 doWork() 将元素重新添加到列表中会发生什么? 我担心的是,正在执行任务的单个线程将在执行任务的线程完成之前终止。这可能意味着遗漏了通过 doWork 函数重新添加到列表中的任何元素。有人知道这是怎么回事吗?

谢谢!

只需将生成器循环嵌入到另一个循环中,并在其间使用 taskwait 以确保所有任务都已完成执行。您还必须确保在代码的并发部分正确锁定链表,例如通过使用关键部分(如下所示)或更细粒度的锁。

doWork(element e)
{
   // ...
   #pragma omp critical(listOps)
   insertElement(linkedList, newElement);
   // ...
}

#pragma omp parallel
{
   #pragma omp single
   {
      do
      {
         #pragma omp critical(listOps)
         while (!empty(linkedList)) {
            element e = removeElement(linkedList);
            #pragma omp task
            doWork(e);
         }
         #pragma omp taskwait
      } while (!empty(linkedList));
   }
}