转载请说明出处:http://blog.csdn.net/cywosp/article/details/9157379
在多线程编程中阻塞队列(Blocking Queue)是一种常用于实现生产者和消费者模型的数据结构。其与普通的队列区别在于,当队列为空时,从队列获取元素的操作将会被阻塞,直到队列中被放入了元素;当队列满时,往队列里存放元素的操作也会被阻塞,直到有元素被从队列中取出(以上的操作都是基于不同的线程来说的,线程在对阻塞队列进程操作时会被阻塞)。下图展示如何通过阻塞队列来合作:
接下来我们用C++11来实现一个简单的阻塞队列(没有容量限制的BlockingQueue)
template<typename T> class BlockingQueue { public: BlockingQueue () : _mutex (), _condvar (), _queue () { } void Put (const T& task) { { std::lock_guard<std::mutex> lock (_mutex); _queue.push_back (task); } _condvar.notify_all (); } T Take () { std::unique_lock<std::mutex> lock (_mutex); _condvar.wait (lock, [this]{return !_queue.empty ();}); assert (!_queue.empty ()); T front (_queue.front ()); _queue.pop_front (); return front; } size_t Size() const { std::lock_guard<std::mutex> lock (_mutex); return _queue.size(); } private: BlockingQueue (const BlockingQueue& rhs); BlockingQueue& operator = (const BlockingQueue& rhs); private: mutable std::mutex _mutex; std::condition_variable _condvar; std::list<T> _queue; };
注:以上代码需要加入下列头文件
#include <condition_variable>
#include <list>
#include <assert.h>
编译时需要加入编译选项 -std=c++0x或者-std=c++11
简单测试程序如下:
将上述代码放到 BlockingQueue.hpp文件中
#include <iostream> #include <thread> #include <future> #include "BlockingQueue.hpp" int main (int argc, char* argv[]) { BlockingQueue<int> q; auto t1 = std::async (std::launch::async, [&q] () { for (int i = 0; i < 10; ++i) { q.Put (i); } }); auto t2 = std::async (std::launch::async, [&q] () { while (q.Size ()) { std::cout << q.Take () << std::endl; } }); auto t3 = std::async (std::launch::async, [&q] () { while (q.Size ()) { std::cout << q.Take () << std::endl; } }); t1.wait (); t2.wait (); t3.wait (); return 0; }
编译: g++ -o blockingqueue -std=c++11 main.cpp BlockingQueue.hpp -pthread
执行blockingqueue得如下结果:
10
23
4
5
6
7
8
9
本篇文章只是简单的实现了阻塞队列的插入函数与获取函数,在java中有线程的BlockingQueue容器可以直接使用,其提供了很多有用的函数(欲知请Google)。
相关推荐
支持多线程的阻塞队列,使用模板技术,可存储任意类型数据
c++11 实现的阻塞队列
std::lock_gurad 是 C++11 中定义的模板类。定义如下: template <class> class lock_guard; lock_guard 对象通常用于管理某个锁(Lock)对象,因此与 Mutex RAII 相关,方便线程对互斥量上锁,即在某个 lock_guard...
c_c++阻塞队列的代码
主要介绍了C++数据结构与算法之双缓存队列实现方法,结合实例形式分析了双缓存队列的原理、实现方法与相关注意事项,需要的朋友可以参考下
阻塞队列是多线程中常用的数据结构,对于实现多线程之间的数据交换、同步等有很大作用。 阻塞队列常用于生产者和消费者的场景,生产者是向队列里添加元素的线程,消费者是从队列里取元素的线程。简而言之,阻塞队列...
C++开发基于TCPsocket实现的web服务器源码。基于TCP socket实现的支持报文解析并返回响应报文的Web服务器,可以响应多种文件需求并能够处理特定的错误情况 服务器实现及其功能: 1、读取配置文件,为服务器自身设置...
下面小编就为大家带来一篇Linux C++ 使用condition实现阻塞队列的方法。小编觉得挺不错的,现在就分享给大家,也给大家做个参考。一起跟随小编过来看看吧
实现基于std::queue ,使用std::mutex和std::condition_variable实现线程安全。 可以使用右值引用调用Produce(T&& item)函数。 Consume(T& item)函数立即返回一个布尔值,表示成功。 ConsumeSync(T& item)方法将...
基于c++及linux网络编程的web服务器源码.zip 基于c++及linux网络编程的web服务器 该web服务器的主要内容如下: 使用了epoll边沿触发+EPOLLONESHOT+非阻塞IO 使用了一个固定线程数的线程池 实现了一个任务队列,...
利用c++模拟进程的调度。...(4 分) 按先进先出方式管理就绪和阻塞队列,按队列输出进程状态 (2 分) 完成可变分区的分配与回收 (3 分) 界面清晰友好 (2 分) 实验结束后撰写实验报告(5 分)。
c++链表实现的阻塞队列 最近从java源码里发现了阻塞队列的实现,觉得非常有趣。 首先,介绍下什么是阻塞队列。阻塞队列代表着一个队列可以线程安全的往该队列中写数据和从该队列中读数据。也就是说,我们可以在多个...
给出就绪队列、阻塞队列及执行进 ****/ /****************** 程的初态: ***********************/ /****************** (2)编写时间片轮转法的调度程序。*******************/ /****************** (3)每次调度后,...
关于操作系统的进程管理的课程设计,内含报告与代码
(4)为了清楚地观察每个进程的调度过程,程序应将每个时间片内的进程的情况显示出来,包括正在运行的进程,处于就绪队列中的进程和处于阻塞队列中的进程。 (5)分析程序运行的结果,谈一下自己的认识。
C++11 加入了线程库,从此告别了标准库不支持并发的历史。然而 c++ 对于多线程的支持还是比较低级,稍微高级一点的用法都需要自己去实现,譬如线程池、信号量等。线程池(thread pool)这个东西,在面试上多次被问到,...
利用简单的结构和控制方法模拟进程结构、进程状态和进程控制。 内容: 1.能够模拟进程的创建与...3.按先进先出方式管理就绪和阻塞队列,能够按队列形式输出进程状态 4.完成可变分区的分配与回收,分配用最佳适应方式;
C ++ 11实现-尽可能移动(而不是复制)元素。 通过模板化,无需专门处理指针-可以为您管理内存。 对元素类型或最大数量没有人为限制。 内存可以预先分配一次,也可以根据需要动态分配。 完全可移植(无需汇编;...
NetLib Linux下的C++网络库功能利用阻塞队列实现的异步日志模块基于pthread封装实现的线程对象实现模板类线程池与函数对象线程池实现基于升序链表的定时器、时间轮定时器、时间堆定时器目录./├── src│ ├── ...