表示一批线程已完成主线程



我想我错过了一个关于多道程序设计的基本设计模式。我找到了一个问题的解决办法,但我认为它过于复杂。

在程序开始时,我会分配一个静态的工作线程池和一个主线程,它们在程序运行的整个过程中都存在。(下面的伪代码)

void *worker(){
   while(1){
   //perworker mutex lock
   //wait for workerSIGNAL
   //do calculations
   //perworker mutex unlock
   }
}

我的主线程向我的所有工作者发出信号,当工作者完成时,他们等待来自主线程的下一个信号。(下面的伪代码)

void *master(){
  while(1){
    //masterMutex lock
    //wait for masterSignal
    //signal all workerthread to start running
    /*
      SHOULD WAIT FOR ALL WORKER THREADS TO FINISH 
      (that is when workers are done with the calculations,
      and are waiting for a new signal) 
     */
    //materMutex unlock
  }
}

我的主线程从代码的另一部分(非线程)获得信号,这意味着只有一个主线程存在。(下面的伪代码)

double callMaster(){
  //SIGNAL masterThread
  //return value that is the result of the master thread
}

我的问题是,如何让主线程等待所有工人完成(等待下一个工人信号)?

我的解决方案非常复杂。我的workerthreads中有一个屏障,它等待所有工作线程完成,然后从我的一个线程(threadId=0)发出信号,在我的主线程底部等待一个workerOne条件。

它很好用,但并不漂亮,任何改进的想法都值得赞赏。

谢谢。

您是否考虑过使用pthread_joinhttp://kernel.org/doc/man-pages/online/pages/man3/pthread_join.3.html?这听起来像是在使用信号在线程之间进行通信。虽然这在某些情况下可能是合适的,但我认为在您的情况下,您可能会发现pthread_join的使用简化了代码。

我在下面概述了一些伪代码示例:

//this goes in your main thread
for (int i = 0; i < num_threads; ++i)
    pthread_join(thread_id[i], ...

这样,主线程将阻塞,直到thread_id数组中的所有线程,即工作线程终止。

您想要使用屏障。屏障用计数N初始化,当任何线程调用pthread_barrier_wait时,它会阻塞,直到总共有N个线程处于pthread_barrier_wait,然后它们都返回,屏障可以再次使用(具有相同的计数)。

有关详细信息,请参阅POSIX中的文档:

http://pubs.opengroup.org/onlinepubs/9699919799/functions/pthread_barrier_wait.html

在Java中,您可以在此处使用初始值等于工作线程数的循环屏障。

对这个屏障的引用被传递给每个工作线程,这些线程在单个工作执行结束时调用barrier.await().

主程序将在barrier处await(),直到所有工作线程都到达执行点并调用barrier.await(.

只有当所有工作线程都调用了barrier.await()时,屏障才会被提升,main才能继续。

循环屏障类似于Latches,只是屏障是循环的,可以无限地重置。因此,在主循环的情况下,循环屏障是一个更好的选择。

最新更新