2013-07-23 53 views
1

所以我想在自定义线程上用C++创建一个同步事件队列。据我所知,boost :: asio :: strand是一个优秀的候选人,有一个转折点:当调用asio :: run()时,它只会在队列中有事件时运行。代码:使用boost :: asio和strands的事件队列:等待新事件

this->control_strand_.reset(new boost::asio::strand(control_io_service_)); 
control_thread_ = boost::thread(boost::bind(&boost::asio::io_service::run,&control_io_service_)); 
control_thread_.join(); 

立即返回。现在我可以去找Boost Asio - How to know when the handler queue is empty?的答案,但是它有一个while-loop-等待它。我宁愿让它更基于事件(也就是说,当队列为空时,等待“包装”调用)。钍只有这样我能想到这样做是完全包住链类,有它触发信号,每当“包装”被称为(像,伪代码)

//some member variables 
boost::condition_variable cond_var; 
boost::mutex mut; 
std::unique_ptr<boost::asio::strand> control_strand_; 
boost::asio::io_service control_io_service_ 
//while loop,running on event processing thread 
void MessageProcessor() 
{ 
    while (true) 
    { 
    { 
     boost::unique_lock<boost::mutex> lock(mut); 
     cond_var.wait(lock); 
    } 
    control_io_service_.run(); 
    } 
} 
//post call,from different thread 
template <typename Handler> 
void wrap(Handler hand) 
{ 
    cond_var.notify_all(); 
    control_strand_->wrap(hand); 
} 

,这将永远运行队列不同时循环(我的同步是有点关闭,但这不是一个问题atm)。有更好,更标准的方法吗?

+1

为什么你不能在'io_service :: work'对象中使用'io_service'? –

+0

@IgorR。男人,每当我尝试做一些事情时,我都会遇到助推器库完成它的问题,但我的搜索技巧似乎错过了它。这看起来像是有效的。 (只需双重检查,这将是一个“隐含链”,即队列是同步排空?)把它放在一个答案中,我会标记它。 – IdeaHat

回答

3

您可以直接使用io_service,它实现了“隐式链”。要保持运行状态,只需给它io_service::work对象,如io_servicereference(请参阅“停止io_service不要用完工作”)。

请注意,io_service是故意线程安全的,因此您可以从外部线程post()函数。