线程2 boost::condition_variable

// 忽略警告
#define _SCL_SECURE_NO_WARNINGS
#pragma warning(disable : 4996)
#include <assert.h>
#include <iostream>
#include <boost/thread.hpp>
#include <stack>
using namespace boost;
using namespace std;

mutex io_mu;
class my_buffer
{
private:
	mutex mu;	// 互斥量
	condition_variable_any cond_put;	// 写如的条件变量
	condition_variable_any cond_get;	// 读取的条件变量
	stack<int> s;						// 缓冲区对象
	int un_read, capacity;
	bool is_full(){ return un_read == capacity; }	// 缓冲区满判断
	bool is_empty(){ return un_read == 0; }			// 缓冲区空判断
public:
	my_buffer(size_t n):un_read(0), capacity(n){}	// 构造函数

	void put(int x)		// 写入数据
	{
		{
			mutex::scoped_lock lock(mu);	// 锁定互斥量
			while (is_full())				// 检查缓冲区是否满
			{
				{	// 锁定cout输出一条信息
					mutex::scoped_lock lock(io_mu);
					cout << "full waiting..." << endl;
				}
				cond_put.wait(mu);			// 条件变量等待 cond_put.wait(mu,!bind(&my_buffer::is_full,this));// 参数2:表达式为真继续等待
			}// 满足条件,停止等待
			s.push(x);	// 写入
			++un_read;
		}// 解锁互斥量,条件变量的通知不需要互斥量锁定
		cond_get.notify_one();	// (执行到该条说明s肯定不空)通知可以读取数据
	}

	void get(int *x)	// 读取数据
	{
		{
			mutex::scoped_lock lock(mu);	// 锁定互斥量
			while (is_empty())				// 检查缓冲区是否空
			{
				{	// 锁定cout输出一条信息
					mutex::scoped_lock lock(io_mu);			// consumer先执行则先锁住
					cout << "empty waiting..." << endl;
				}
				cond_get.wait(mu);			// 条件变量等待 cond_get.wait(mu,!bind(&my_buffer::is_empty,this));
			}// 满足条件,停止等待
			*x = s.top();	// 读取
			--un_read;
			s.pop();		// 出栈
		}// 解锁互斥量,条件变量的通知不需要互斥量锁定
		cond_put.notify_one();	// (执行到该条说s明肯定不满)通知可以写入数据
	}
};

my_buffer buf(5);
// 然后定义两个生产者和消费者
// 生产者
void producer(int n)
{
	for (int i = 0; i < n; ++i)
	{
		{
			mutex::scoped_lock lock(io_mu);
			cout << "put:	" << i << endl;	 // cout只是为了接下来的bug.put提供消息 
		}
		buf.put(i);	// 写入数据
	}
}
// 消费者
void consumer(int n)
{
	int x;
	for (int i = 0; i < n; ++i)
	{
		buf.get(&x);
		mutex::scoped_lock lock(io_mu);
		cout << "get:	" << x << endl;
	}
}
int main()
{

	// 条件变量condition_variable; condition_variable_any(适应更多的互斥类型);
	// 拥有条件变量cv的线程先锁定互斥量,循环检查某个条件,否则cv的成员函数wait()等待直到条件满足
	// 当其他线程满足条件变量的条件时,调用notify_one或notify_all通知相关线程继续执行
	
	// 1.mutex::scoped_lock lock(io_mu);四处同一时刻只有一处加锁
	// 2 例如.t1线程持有io_mu对象后,在自己的时间片里执行临界区代码;t1时间片到了会切换到其他线程t2
	// 3.在t2的时间片期间执行代码,如果t2也有mutex::scoped_lock lock(io_mu),而t1还没执行完{临界区的代码},则t2会在该行代码处等待直到时间片用完
	// 4.当再次切换到t1时,t1继续执行临界区剩下的代码,直到走出临界区(跳出lock作用域),当t1走完时间片后,且没有再持有io_mu对象时,切换到t2时间片执行mutex::scoped_lock lock(io_mu),上锁
	// 5.t2线程执行2步骤..
	thread t1(producer,20);	// 一个生产者线程
	thread t2(consumer,10);	// 两个消费者线程
	thread t3(consumer,10);

	// producer 和 consumer随机先一个执行
	t1.join();
	t2.join();
	t3.join();
	return 0;
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值