生产者-消费者问题(操作系统)

article/2025/11/10 2:50:59

生产者-消费者问题从特殊到一般(从易到难)可以分3种形式:

一个生产者、一个消费者、一个缓冲区的问题;

一个生产者、一个消费者、n个缓冲区的问题;

 k个生产者、m个消费者、n个缓冲区的问题;

当缓冲区空时,生产者可将产品存入缓冲区;当缓冲区满时,生产者必须等待 (阻塞),待消费者取走产品后将其唤醒后,才能将产品存入。

当缓冲区有产品时,消费者可从缓冲区取出产品进行消费;当缓冲区空时,消费者必须等待 ( 阻塞 ) ,待生产者存入产品后将其唤醒后,才能再从缓冲区取产品。

1. 为生产者设置 1 个私有信号量 empty ,其初值为 1 ,表示有 1 个空缓冲区;为消费者设置 1 个私有信号量 full ,其初值为 0 ,表示开始时没有满缓冲区;( 信号量初值由物理意义确定
2. 生产者将产品存入缓冲区之前,应先 测试 缓冲区是否空:执行 wait(empty) 操作;离开临界区 ( 存入产品 ) 后,应 通知 ( 可能会唤醒 ) 消费者:执行 signal(full) 操作;
3. 消费者从缓冲区取产品之前,应先 测试 缓冲区是否满:执行 wait(full) 操作;离开临界区 ( 取走产品 ) 后,应 通知 ( 可能会唤醒 ) 生产者:执行 signal(empty) 操作

一个生产者、一个消费者、一个缓冲区


生产者消费者问题的算法描述如下所示:

初始化设置

semaphore empty,full;
empty=1;full=0;

生产者

parbegin
process Producer:
{ produce an item in nextp;wait(empty);//测试buffer=nextp;signal(full);//通知消费者
}

消费者

process Consumer:
{wait(full); //测试nextc=buffer;signal(empty); //通知consume the itemin nextc;
}
parend

信号量机制解决进程同步问题的一般方法:

1. 为同步双方设置各自的信号量,初值为其初始状态可用的资源数 ( 故该信号量称为 资源信号量 私有信号量 )
2. 同步双方任一进程在进入临界区之前,应先对自己的信号量执行 wait(< 己方信号量 >) 操作,以 测试 是否有自己可用的资源。若有资源可用,则进入临界区,否则阻塞;
3.同步双方任一进程离开临界区后,应对合作方 (对方)的信号量执行signal(<对方信号量>)操作,以通知(若对方处于阻塞状态,则唤醒它)对方已有资源可用(对方已可进入临界区)。

一个生产者、一个消费者、n个缓冲区


        为生产者设置一个资源信号量empty ,其初值为生产者的可用资源数 ( 空缓冲区的个数 )n ,即 empty=n
        为消费者设置一个资源信号量full ,其初值为消费者的可用资源数 ( 满缓冲区的个数 )0 ,即 full=0

生产者消费者问题的算法描述如下所示:

初始化设置

​​​​​​​semaphore empty,full;
empty=n;full=0;
int in=0,out=0;   //下标

生产者

parbegin
process Producer:
{ produce an item in nextp;wait(empty);//测试buffer[in]=nextp;in=(in+1)%n;signal(full);//通知消费者
}

消费者

process Consumer:
{wait(full); //测试nextc=buffer[out];out=(out+1)%n;signal(empty); //通知consume the item in nextc;
}
parend

本题中inout不是共享变量(因为只有一个生产者和一个消费者),无需互斥访问。

K个生产者、M个消费者、n个缓冲区


1、设置生产者的资源信号量 empty ,其初值为 n ,表示开始时有 n 个空缓冲区;
2、设置消费者的资源信号量 full ,其初值为 0 ,表示开始时有 0 个满缓冲区;
3、只要有空的缓冲区,生产者便可将消息送入缓冲区;
4、只要有满的缓冲区,消费者便可从缓冲区取走一个消息。
5、用互斥信号量 mutex 对缓冲区 ( 共享变量 in out) 的互斥使用,互斥信号量 mutex 初值为 1
6、生产者用共享变量 in 作为下标访问缓冲区, mutex 为其互斥信号量;消费者用共享变量 out 作为下标访问缓冲区,其互斥信号量也用 mutex

初始化

semaphore mutex,empty,full ;
item buffer[n] ;
int in = 0,out = 0 ;
mutex.value = 1;
empty.value=n,full.value=0;

生产者

parbegin //并发执行开始 
process produceri (i=1,2,…,k)  //生产者进程
{item nextp;while (true){  produce an item nextp;wait(empty) ;	//测试是否有可用的资源wait(mutex);	    //互斥(进入临界区)buffer[in] = nextp ;in = (in + 1)% n ;signal(mutex) ;  //退出临界区signal(full) ;	//通知(可能唤醒)协作方}
} 

消费者

process consumerj (j=1,2,…,m)
{  item nextc ;while (true)   {wait(full); //测试是否有可用的资源wait(mutex);nextc = buffer[out] ;out = (out + 1)% n ;signal(mutex);//生产者消费者互斥访问缓冲区,同时生产者互斥生产,消费者户次消费signal(empty); //通知(可能唤醒)协作方consume the item in nextc ;}
}
parend //并发执行结束 

注意:


在每个进程中,实现互斥的 wait(mutex) signal(mutex) 必须成对出现;
对资源信号量 empty和full wait signal 操作也要成对地出现,但它们处于不同的进程中 ( 交叉成对 )
在每个进程中的多个 wait 操作顺序不能颠倒,应先执行对资源信号量(也称私有信号量)的 wait 操作,然后执行对互斥信号量(公有信号量)的 wait 操作,否则可能引起进程死锁。

重申信号量解决同步问题的要点:


1. 为同步双方设置各自的信号量,初值为其初始状态可用的资源数 ( 故该信号量称为 资源信号量 私有信号量 )
2. 同步双方任一进程在进入临界区之前,应先对自己的资源信号量执行 wait(< 己方信号量 >) 操作,以 测试 是否有自己可用的资源。若有资源可用,则进入临界区,否则阻塞;
3. 同步双方任一进程离开临界区后,应对合作方 ( 对方 ) 的资源信号量执行 signal(< 对方信号量 >) 操作,以 通知 ( 若对方处于阻塞状态,则唤醒它 ) 对方已有资源可用 ( 对方已可进入临界区 )


http://chatgpt.dhexx.cn/article/wd6qPKKB.shtml

相关文章

Java多线程——生产者消费者问题

创建多个线程去执行不同的任务&#xff0c;如果这些任务之间有着某种关系&#xff0c;那么线程之间必须能够通信来协调完成工作。 生产者消费者问题&#xff08;英语&#xff1a;Producer-consumer problem&#xff09;就是典型的多线程同步案例&#xff0c;它也被称为有限缓冲…

生产者-消费者问题(详解)

目录 1.问题描述 2.问题分析 3.问题实现 3.1 初始化 3.2 生产者 3.3 消费者 1.问题描述 要求如下&#xff1a; 只要缓冲区没满&#xff0c;生产者才能把产品放入缓冲区&#xff0c;否则必须等待。只有缓冲区不空时&#xff0c;消费者才能从中取出产品&#xff0c;否则必…

【操作系统】生产者消费者问题

生产者消费者模型 文章目录 生产者消费者模型 [toc]一、 生产者消费者问题二、 问题分析三、 伪代码实现四、代码实现&#xff08;C&#xff09;五、 互斥锁与条件变量的使用比较 一、 生产者消费者问题 生产者消费者问题&#xff08;英语&#xff1a;Producer-consumer proble…

Sublime Text实现代码自动生成,快速编写HTML/CSS代码

目录 下载Sublime Text安装emmet插件常用自动生成HTML代码实例初始化页面自动补全标签配对自动添加类名和id名自动填充文本内容自动生成同级标签自动生成嵌套标签自动生成提级标签自动生成分组标签自动生成多个元素自动生成带多个属性的元素自动生成隐式标签 常用自动生成CSS代…

MybatisPlus代码自动生成

这里写自定义目录标题 前言一. 什么是 MyBatis-Plus二.MybatisPlus 代码自动生成①idea 插件生成1. 插件2.连接数据源3.生成代码 ②配置工具类生成 前言 最开始&#xff0c;要在 Java 中使用数据库时&#xff0c;需要使用 JDBC&#xff0c;创建 Connection、ResultSet 等&…

Simulink自动代码生成:生成代码的基本设置

Simulink自动代码生成也被称作基于模型开发&#xff08;BMD&#xff09;&#xff0c;相比于传统的手写代码方式能够尽量减少人为错误。模型本身可以用于仿真&#xff0c;单元测试等&#xff0c;更便于提前发现逻辑错误。同时只要约定好模型接口&#xff0c;就可以多人协作&…

C语言代码自动生成工具

一、模型建模模块&#xff1a; 基于开源开发平台Eclipse&#xff0c;以图形方式创建和编辑模型元素&#xff0c;模型元素如下&#xff1a; 活动&#xff1a;初始活动、简单活动、复杂活动、结束活动&#xff1b;状态&#xff1a;初始状态、状态、结束状态&#xff1b;变迁&a…

前端代码自动生成器

场景 1.CodeFun是什么 CodeFun是一款UI 设计稿智能生成源代码的工具,支持微信小程序端、移动端H5和混合APP,上传 Sketch、PSD等形式的设计稿&#xff0c;通过智能化技术一键生成可维护的前端代码. 2.学习成本高吗&#xff1f; 对于前端工程师来说&#xff0c;几乎没有学习成本…

MATLAB/Simulink自动代码生成(一)

Simulink自带了种类繁多、功能强大的模块库&#xff0c;在基于模型设计的开发流程下&#xff0c;Simulink不仅通过仿真可以进行早期设计的验证&#xff0c;还可以生成C/C、PLC等代码直接应用于PC、MCU、DSP等平台。在嵌入式软件开发中发挥着重要的作用&#xff0c;本文以Simuli…

IDEA自动生成代码插件

官方介绍 基于IntelliJ IDEA开发的代码生成插件&#xff0c;支持自定义任意模板&#xff08;Java&#xff0c;html&#xff0c;js&#xff0c;xml&#xff09;。 只要是与数据库相关的代码都可以通过自定义模板来生成。支持数据库类型与java类型映射关系配置。 支持同时生成生…

Matlab/Simulink自动生成C代码实验

目录 0. 概要 1. Matlab /Simulink/Embedded Coder关系与区别 2. 搭建Simulink模型及仿真 2.1 搭建模型 2.2 仿真 3. 生成代码 3.1 求解器设置为定步长 3.2 安装 MinGW-w64 编译器 3.3 调出Simulink Coder 4. 工具都生成了啥呢&#xff1f; 0. 概要 Matlab网站提供了很多…

关于RuoYi自动代码生成功能的使用

为什么要使用代码生成&#xff1f; 答&#xff1a;因为在后端构建的过程中会有许多重复的类似的代码编写&#xff0c;而我们如果一个个去编写&#xff0c;会耗费大量时间与精力&#xff0c;所以我们可以设计一个功能去自动生成这些重复的&#xff0c;简单的代码。而若依系统就…

Mybatis Plus自动生成代码

mybatis-plus自动生成代码 一、简易生成代码二、指定生成的样式&#xff0c;并且不在一个模块1.父pom文件配置2.子模块pom文件配置3.准备vm文件4.设置MyBatisPlusGenerator.java5.运行MyBatisPlusGenerator.java文件6.运行sign-auth模块,解决异常 一、简易生成代码 /*** 代码生…

Simulink自动代码生成:数据类型别名自定义

在手写代码时&#xff0c;我们经常能看到自定义数据类型别名&#xff0c;例如有些代码中将计算机默认的数据类型改为我们自己习惯的名称&#xff0c;如图所示。 目录 一. 系统默认生成的别名二. 建立Simulink AliasType三. 修改Data Type Replacement四. 数据类型别名修改后的…

Simulink 自动代码生成原理

如下图&#xff0c;Simulink模型会先变成一个文本式的 .rtw 模型描述文件&#xff0c;然后再变成 .c,.h&#xff0c;最后编译为最终目标文件。 典型的 Simulink 用户通常都是&#xff0c;用Simulink设计好算法后&#xff0c;做到生成源代码这一步。然后把生成的算法的.c .h 源代…

如何自动生成SpringBoot项目代码

目录 1.RuoYi源码下载及启动若依服务1.1. RuoYi源码下载1.2. 启动若依服务 2.自动生成代码3.代码及sql文件链接 已经工作一段时间啦&#xff01;首先是从后端开发开始入手的&#xff0c;前端也是在自学阶段&#xff08;边学边问我身边的同事大佬&#xff09;&#xff0c;努力是…

Simulink自动代码生成:数据字典的建立及代码优化

在上一节《Simulink自动代码生成&#xff1a;生成代码的基本设置》的基础上&#xff0c;我们来对模型进行优化&#xff0c;使得生成的代码更能满足实际的需求&#xff0c;没看过我上一篇文章的可以点开如下链接&#xff1a;   Simulink自动代码生成&#xff1a;生成代码的基本…

推荐几个代码自动生成器

文章目录 老的代码生成器的地址&#xff1a;[https://www.cnblogs.com/skyme/archive/2011/12/22/2297592.html](https://link.zhihu.com/?targethttps%3A//www.cnblogs.com/skyme/archive/2011/12/22/2297592.html)1.懒猴子CG2.IT猿网3.listcode4.magicalcoder5.CodeSmith6. …

Mybatis代码自动生成

新启动的项目,数据库设计可能随时会变动,一些基础的接口,特别是xml文件和映射对象也需要变动,改动工作量大,用mybatis-plus代码自动生成工具自动生成代码,大大提高了效率 自动生成代码工具使用过程记录如下 首先手动创建一个springboot项目,可以去springboot官网上生成,也可以…

Simulink 自动代码生成电机控制:基于Keil软件集成

目录 系统软件架构 1.应用层全模型生成&#xff0c;底层手写代码 2.应用层模型生成&#xff0c;底层也是基于模型生成 3.Autosar 软件集成操作 接口配置 总结 系统软件架构 嵌入式软件开发包含应用层和底层&#xff0c;目前基于模型的开发软件架构总结为以下几种: 1.应…