【发布时间】:2013-07-23 05:56:45
【问题描述】:
这是使用VS 2010并发队列的典型生产者/消费者模式,问题是当我运行程序时,内存消耗超过1GB然后程序崩溃,有人可以指出这段代码中的问题吗?
#include <iostream>
#include <fstream>
#include <string>
#include <cstdlib>
#include <ctime>
#include <boost\shared_ptr.hpp>
#include <boost\thread.hpp>
#include <concurrent_queue.h>
void wait2(int milliseconds)
{
boost::this_thread::sleep(boost::posix_time::milliseconds(milliseconds));
}
class CQueue
{
Concurrency::concurrent_queue<int> Q;
boost::mutex m;
boost::condition_variable cv;
public:
CQueue():QValue(-1)
{
}
int QRead()
{
while(Q.empty())
{
boost::unique_lock<boost::mutex> lk(m);
cv.wait(lk);
}
int res;
if(Q.try_pop(res))
{
QValue = res;
return true;
}
return false;
}
void QWrite(int i)
{
Q.push(i);
cv.notify_one();
}
int QValue;
};
CQueue myqueue;
void write()
{
int i = 0;
while(true)
{
myqueue.QWrite(++i);
}
}
void read()
{
while(true)
{
if( myqueue.QRead())
std::cout << myqueue.QValue << std::endl;
else
std::cout << "failed to read" << std::endl;
}
}
void main ()
{
boost::thread w(write);
boost::thread r(read);
w.join();
r.join();
}
【问题讨论】:
-
没有明显的死锁。可能由于读取器正在执行 I/O,写入器填充队列的速度比读取器消耗队列的速度要快得多。
-
你为什么把
unique_lock放在一个范围内,你知道你会在锁关闭的时候从队列中读取,对吧?既然已经有了 concurrent_queue,为什么还要做这些事情? -
@Casey 你应该是正确的,因为通常生产者/消费者模式需要指定每个消费者的容量(他们的输入 fifo 的阈值),以便阻止生产者,直到有人准备好或有存储空间。
-
@Casey,该程序在大约 77k 次插入时失败,这并不大,所以我不认为这是个问题。
-
@yngum、unique_lock 和 condition_variable 是在队列为空时挂起线程以避免繁忙 cpu 所必需的。
标签: c++ multithreading boost queue