我正在开发一个使用线程安全队列的项目。这基本上是一个生产者/消费者问题。
我的代码目前做的是
void threadCode()//the consumer
{
while(active) // active is an atomic int, we use it to turn off everything during destruction
{
threadSafeQueue.popFront();//if queue is empty, it will wait for a signal.The queue has a CV.
// process it
// if it fails to process it but less than three times,
// put it back to the queue to retry later
}
}
问题是,当我的析构函数将 active 更改为 0 时,即使队列不为空,所有线程也会被终止。比如处理item失败,放回队列,此时active为0。
我不希望这样的事情发生。我希望在处理队列中的所有内容后销毁该实例。
所以我试了一下,
void threadCode()
{
while( active || queue.size() != 0 )
{ //[1]
queue.popFront();
//process
// put it back to the queue if it fails less than 3 times
}
}
queue.size() 和 queue.popFront() 是线程安全的。但是将它们放在一起并不是...如果队列中只剩下一件事并且上下文切换发生在 [1] 处。该线程可能会永远休眠。
因为我在析构函数中有类似 threadpool.join() 的东西,而且那个线程永远不会醒来。问题就停留在那里。
我想知道有没有人有更好的办法来解决这个问题?
谢谢!!
最佳答案
不是让消费者线程检查外部标志,而是让队列本身维护一个内部“关闭”标志。如果没有更多工作要处理,则 .popFront()
函数返回“正在关闭”状态而不是要处理的项目。
关于c++ - 生产者/消费者,如何确保在关闭所有消费者之前耗尽线程安全队列?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37647223/