C++多线程编程(第三章 案例2,条件变量,生产者-消费者模型)

目录

1、condition_variable

等待中,增加了时延和开销,用条件变量就很快及时处理

1.1、生产者消费者模型

生产者和消费者共享资源变量(list队列);

生产者生产一个产品,通知消费者消费;

消费者阻塞等待信号,获取信号后消费产品(取出list队列中数据)

1.2、改变共享变量的线程步骤

准备好信号量

bash 复制代码
std::condition_variable cv;

1、获取std::mutex(常用std::unique_lock)

bash 复制代码
unique_lock lock(mux);

2、在获取锁时进行修改;

bash 复制代码
msgs_.push_back(data);

3、释放锁并通知读取线程

bash 复制代码
lock.unlock();
cv.notify_one();//通知一个等待信号线程
cv.notify_all;//通知所有等待信号线程

1.3、等待信号读取共享变量的线程步骤

1.3.1、获得改变共享变量线程共同的mutex

unique_lock lock(mux);

1.3.2、wait()等待信号通知

1.3.2.1、无lambda表达式
cpp 复制代码
//解锁lock,并阻塞等待notify_one notify_all 通知
cv.wait(lock);

//接收到通知会再次获取锁标注,也就是说如果此时mux资源被占用,wait函数会阻塞
msgs_front();
//处理数据
msgs_pop_front();
1.3.2.2 lambda表达式
bash 复制代码
cv.wait(lock,[]{return !msgs_empty();})

只在std::unique_lockstd::mutex上工作的std::condition_variable

样例代码

cpp 复制代码
#include <thread>
#include <iostream>
#include <mutex>
#include <list>
#include <string>
#include <sstream>

using namespace std;
list<string> msgs_;
mutex mux;
condition_variable cv;//条件变量

void ThreadWrite()
{
	for (int i = 0;;i++)
	{
		stringstream ss;
		ss << "Write msg " << i;

		unique_lock<mutex> lock(mux);

		msgs_.push_back(ss.str());
		lock.unlock();//解锁
		cv.notify_one();//通知一个

		this_thread::sleep_for(1ms);
	}
}
void ThreadRead(int i)
{
	for (;;)
	{
		cout << "Read msg" << endl;
		unique_lock<mutex> lock(mux);
		cv.wait(lock);//解锁、阻塞等待信号

		mambda表达式方式
		//cv.wait(lock, [i]
		//{
		//	cout << i << " wait" << endl;//特别这句话在啥时候会进入,调用多少次,搞不清楚就用上面cv.wait更简单
		//	//return true;//只要返回true,wait就不会阻塞
		//	return !msgs_.empty();
		//	
		//	});

		//获取信号后锁定
		while (!msgs_.empty())
		{

			cout << i << "read " << msgs_.front() << endl;
			msgs_.pop_front();
		}
		if (msgs_.empty()) return;
	}
}

int main()
{

	thread th(ThreadWrite);
	th.detach();
	for (int i = 0; i < 3; i++)
	{//读取线程
		thread th2(ThreadRead,i+1);
		th2.detach();
	}

	getchar();
	return 0;
}

期间出差了一个月,没有时间学习,今天开始又继续学习和做笔记了...

辉2023.9.8

相关推荐
老四啊laosi6 小时前
[C++进阶] 24. 哈希表封装unordered_map && unordered_set
c++·哈希表·封装·unordered_map·unordered_set
014-code6 小时前
订单超时取消与库存回滚的完整实现(延迟任务 + 状态机)
java·开发语言
妙为6 小时前
银河麒麟V4下编译Qt5.12.12源码
c++·qt·国产化·osg3.6.5·osgearth3.2·银河麒麟v4
lly2024066 小时前
组合模式(Composite Pattern)
开发语言
游乐码7 小时前
c#泛型约束
开发语言·c#
Dontla7 小时前
go语言Windows安装教程(安装go安装Golang安装)(GOPATH、Go Modules)
开发语言·windows·golang
chushiyunen7 小时前
python rest请求、requests
开发语言·python
铁东博客7 小时前
Go实现周易大衍筮法三变取爻
开发语言·后端·golang
baidu_huihui7 小时前
在 CentOS 9 上安装 pip(Python 的包管理工具)
开发语言·python·pip
南 阳7 小时前
Python从入门到精通day63
开发语言·python