生产者消费者问题操作系统课程设计
生产者消费者问题操作系统课程设计
目录1 绪论 (1)1.1 实现的功能 (1)1.2 P V 操作 (1)2 生产者——消费者问题。
(2)2.1 要求 (2)2.2 生产者和消费者两个进程的程序 (2)2.3进程控制块PCB。
(3)2.4处理器的模拟。
(3)2.5程序设计 (3)3设计步骤 (4)3.1课程分析 (5)3.1.2 流程图 (5)3.1.3 测试程序 (7)3.1.4测试结果分析 (12)5 结论 (12)参考文献 (13)1 绪论生产者-消费者问题是一个经典的进程同步问题,该问题最早由Dijkstra提出,用以演示他提出的信号量机制。
模拟实现用同步机构避免发生进程执行时可能出现的与时间有关的错误。
进程是程序在一个数据集合上运行的过程,进程是并发执行的,也即系统中的多个进程轮流地占用处理器运行。
我们把若干个进程都能进行访问和修改的那些变量称为公共变量。
由于进程是并发地执行的,所以,如果对进程访问公共变量不加限制,那么就会产生“与时间有关”的错误,即进程执行后所得到的结果与访问公共变量的时间有关。
为了防止这类错误,系统必须要用同步机构来控制进程对公共变量的访问。
一般说,同步机构是由若干条原语——同步原语——所组成。
本实习要求学生模拟PV操作同步机构的实现,模拟进程的并发执行,了解进程并发执行时同步机构的作用。
1.1 实现的功能生产者-消费者问题是一个经典的进程同步问题,有m个生产者和n个消费者,它们共享可存放k件产品的缓冲区。
生产者进程生产物品,然后将物品放置在一个空缓冲区中,供消费者进程消费。
消费者进程从缓冲区中获得物品,然后释放缓冲区。
当生产者进程生产物品时,如果没有空缓冲区可用,那么生产者进程必须等待消费者线程释放出一个空缓冲区。
当消费者进程消费物品时,如果没有满的缓冲区,那么消费者进程将被阻塞,直到新的物品被生产出来。
1.2 P V 操作(1) PV操作同步机构,由P操作原语和V操作原语组成,它们的定义如下:P操作原语P (s):将信号量s减去1,若结果小于0,则执行原语的进程被置成等待信号量s的状态。
操作系统课程设计生产者消费者
生产者消费者问题 (Producer-consumer problem) , 也称有限缓冲问题 (Bounded-buffer problem),是一个多线程同步问题的经典案例。 该问题描述了两个共享固定大小缓冲区的线程——即所谓的“生产者”和“消费者”— —在实际运行时会发生的问题。 生产者的主要作用是生成一定量的数据放到缓冲区中, 然后 重复此过程。与此同时,消费者也在缓冲区消耗这些数据。该问题的关键就是要保证生产者 不会在缓冲区满时加入数据,消费者也不会在缓冲区中空时消耗数据。 要解决该问题,就必须让生产者在缓冲区满时休眠(或者放弃数据),等到下次消费者 消耗缓冲区中的数据的时候,生产者才能被唤醒,开始往缓冲区添加数据。同样,也可以让 消费者在缓冲区空时进入休眠,等到生产者往缓冲区添加数据之后,再唤醒消费者。通常采 用进程间通信的方法解决该问题,常用的方法有信号灯法等。如果解决方法不够完善,则容 易出现死锁的情况。出现死锁时,两个线程都会陷入休眠,等待对方唤醒自己。该问题也能 被推广到多个生产者和消费者的情形。
5
pthread_mutex_lock(&lock); while (q->num == 0) { pthread_cond_wait(&empty, &lock); } sem_wait(&product_number); q->front = (q->front + 1) % NUM; char c = q->productc[q->front]; q->productc[q->front] = ' '; q->num--; printf("消费者 1 显示内容: %c\n", c); printf("产品数量:%d\n", q->num); sem_post(&blank_number); if (q->num == NUM - 1) { pthread_cond_signal(&full); } pthread_mutex_unlock(&lock); sleep(rand() % 2); } } void *consumer2(void *arg) { struct P_Queue *q; q = (struct P_Queue *) arg; while (1) { pthread_mutex_lock(&lock); while (q->num == 0) { pthread_cond_wait(&empty, &lock); } sem_wait(&product_number); q->front = (q->front + 1) % NUM; char c = q->productc[q->front]; char d = 0; if(c>=65 && c<=90) { d = c+32;} else { d = c-32;} q->productc[q->front] = ' '; q->num--; printf("消费者 2 更改大小写:%c---%c\n", c,d); printf("产品数量:%d\n", q->num); sem_post(&blank_number); if (q->num == NUM - 1) { pthread_cond_signal(&full); }
生产者消费者问题操作系统课程设计
目录1 绪论 (3)1.1 实现的功能 (3)1.2 P V 操作 (3)2 生产者——消费者问题。
(4)2.1 要求 (4)2.2 生产者和消费者两个进程的程序 (4)2.3进程控制块PCB。
(5)2.4处理器的模拟。
(5)2.5程序设计 (6)3设计步骤 (7)3.1课程分析 (7)3.1.2 流程图 (7)3.1.3 测试程序 (9)3.1.4测试结果分析 (14)5 结论 (15)参考文献 (16)1 绪论生产者-消费者问题是一个经典的进程同步问题,该问题最早由Dijkstra提出,用以演示他提出的信号量机制。
模拟实现用同步机构避免发生进程执行时可能出现的与时间有关的错误。
进程是程序在一个数据集合上运行的过程,进程是并发执行的,也即系统中的多个进程轮流地占用处理器运行。
我们把若干个进程都能进行访问和修改的那些变量称为公共变量。
由于进程是并发地执行的,所以,如果对进程访问公共变量不加限制,那么就会产生“与时间有关”的错误,即进程执行后所得到的结果与访问公共变量的时间有关。
为了防止这类错误,系统必须要用同步机构来控制进程对公共变量的访问。
一般说,同步机构是由若干条原语——同步原语——所组成。
本实习要求学生模拟PV操作同步机构的实现,模拟进程的并发执行,了解进程并发执行时同步机构的作用。
1.1 实现的功能生产者-消费者问题是一个经典的进程同步问题,有m个生产者和n个消费者,它们共享可存放k件产品的缓冲区。
生产者进程生产物品,然后将物品放置在一个空缓冲区中,供消费者进程消费。
消费者进程从缓冲区中获得物品,然后释放缓冲区。
当生产者进程生产物品时,如果没有空缓冲区可用,那么生产者进程必须等待消费者线程释放出一个空缓冲区。
当消费者进程消费物品时,如果没有满的缓冲区,那么消费者进程将被阻塞,直到新的物品被生产出来。
1.2 P V 操作(1) PV操作同步机构,由P操作原语和V操作原语组成,它们的定义如下:P操作原语P (s):将信号量s减去1,若结果小于0,则执行原语的进程被置成等待信号量s的状态。
操作系统课程设计“生产者-消费者”问题
《操作系统》课程设计题目:“生产者-消费者”问题学院:信息工程学院专业:计算机科学与技术班级:计科1302*名:***指导老师:***2016年1月 15日目录一、课程设计目标 (2)二、课题内容 (2)1.实验目的 (2)2、实验环境 (2)3、实验要求 (2)三、设计思路 (3)1.信号量的设置 (3)2.系统结构 (4)3.程序流程图 (5)4.P V操作代码 (6)四、源代码 (7)五、运行与测试 (10)六、心得体会 (12)一、课程设计目标学习System V的进程间通信机制,使用信号量和共享内存实现经典进程同步问题“生产者-消费者”问题。
具体要求:1.创建信号量集,实现同步互斥信号量。
2.创建共享内存,模拟存放产品的公共缓冲池。
3.创建并发进程,实现进程对共享缓冲池的并发操作。
二、课题内容1.实验目的(1)掌握基本的同步互斥算法,理解生产者和消费者同步的问题模型。
(2)了解linux中多线程的并发执行机制,线程间的同步和互斥。
2、实验环境:C/C++语言编译器3、实验要求(1)创建生产者和消费者线程在linux环境下,创建一个控制台进程,在此进程中创建n个线程来模拟生产者或者消费者。
这些线程的信息由本程序定义的“测试用例文件”中予以指定。
(2)生产和消费的规则在按照上述要求创建线程进行相应的读写操作时,还需要符合以下要求:①共享缓冲区存在空闲空间时,生产者即可使用共享缓冲区。
②从上边的测试数据文件例子可以看出,某一生产者生产一个产品后,可能不止一个消费者,或者一个消费者多次地请求消费该产品。
此时,只有当所有的消费需求都被满足以后,该产品所在的共享缓冲区才可以被释放,并作为空闲空间允许新的生产者使用。
③每个消费者线程的各个消费需求之间存在先后顺序。
例上述测试用例文件包含一行信息“5 C 3 l 2 4”,可知这代表一个消费者线程,该线程请求消费1,2,4号生产者线程生产的产品。
而这种消费是有严格顺序的,消费1号线程产品的请求得到满足后才能继续往下请求2号生产者线程的产品。
现代操作系统课程设计报告 生产者与消费问题
进程同步模拟设计——生产者和消费者问题第一章课设任务本课程设计的任务在于,通过编写一个具体的有关操作系统进程同步互斥的经典问题,加强对操作系统实现进程间同步与互斥的机制的理解。
同时培养提出问题、发现知识、使用工具、解决问题的能力。
具体地,我们要编制出一个程序,利用PV原语以及进程创建、同步、互斥、销毁等相关的系统调用来模拟“生产者—消费者”问题。
第二章背景介绍2.1 “生产者—消费者”问题(the producer-consumer problem)生产者-消费者(producer-consumer)问题,也称作有界缓冲区(bounded-buffer)问题,两个进程共享一个公共的固定大小的缓冲区。
其中一个是生产者,用于将消息放入缓冲区;另外一个是消费者,用于从缓冲区中取出消息。
问题出现在当缓冲区已经满了,而此时生产者还想向其中放入一个新的数据项的情形,其解决方法是让生产者此时进行休眠,等待消费者从缓冲区中取走了一个或者多个数据后再去唤醒它。
同样地,当缓冲区已经空了,而消费者还想去取消息,此时也可以让消费者进行休眠,等待生产者放入一个或者多个数据时再唤醒它。
问题分析:该问题涉及到操作系统进程管理当中的两个重要概念——同步和互斥。
同步,表现在生产者和消费者需要协同工作,步调不能拉开太大(由缓冲区大小n决定,n越大,缓冲空间越大,步调可以拉得越开;n=1时,必须是生产一个,消费一个,生产者和消费者就完全同步了)。
当步调差距超过极限时,走在前面的当前进程(生产者)调用P 原语时由于资源耗尽,被阻塞;步调靠后的继续向前推进。
由此实现同步。
互斥,表现在生产者与消费者、生产者与生产者、消费者与消费者任何两个成员之间必须互斥地使用缓冲区。
当有一个成员进入缓冲区存/取产品时,其他成员将被关在门外排队等候(被阻塞);当完毕时,通知队首成员进入。
由操作系统理论可知,我们需要三个信号量,分别命名full, empty, mutex,来分别代表消费者的可用资源数、生产者的可用资源数、缓冲区是否可用。
计算机操作系统课程设计报告《生产者---消费者问题》
计算机操作系统课程设计报告《生产者---消费者问题》《计算机操作系统》课程设计题目:生产者---消费者问题专业:软件工程年级:2010级小组成员: A B指导教师:时间:地点:2012年5 月摘要生产者消费者问题(英语:Producer-consumer problem),也称有限缓冲问题(英语:Bounded-buffer problem),是一个多线程同步问题的经典案例。
该问题描述了两个共享固定大小缓冲区的线程——即所谓的“生产者”和“消费者”——在实际运行时会发生的问题。
生产者的主要作用是生成一定量的数据放到缓冲区中,然后重复此过程。
与此同时,消费者也在缓冲区消耗这些数据。
该问题的关键就是要保证生产者不会在缓冲区满时加入数据,消费者也不会在缓冲区中空时消耗数据。
生产者消费者模式是通过一个容器来解决生产者和消费者的强耦合问题。
生产者和消费者彼此之间不直接通讯,而通过阻塞队列来进行通讯,所以生产者生产完数据之后不用等待消费者处理,直接扔给阻塞队列,消费者不找生产者要数据,而是直接从阻塞队列里取,阻塞队列就相当于一个缓冲区,平衡了生产者和消费者的处理能力。
目录1. 概述 (4)2. 课程设计任务及要求 (4)2.1 设计任务 (4)2.2 设计要求 (4)2.3 分工日程表 (4)3. 算法及数据结构 (5)3.1算法的总体思想 (5)3.2 生产者模块 (5)3.3 消费者模块 (7)4. 程序设计与实现 (8)4.1 程序流程图 (8)4.2 程序代码 (9)4.3 实验结果 (14)5. 结论 (17)6. 收获、体会和建议 (17)6.1收获......................................... 错误!未定义书签。
7. 参考文献 (18)1. 概述本课题设计是完成了“操作系统原理”课程进行的一次全面的综合训练,通过这次课程设计,充分检验学生对课程的掌握程度和熟练情况,让学生更好的掌握操作系统的原理及其实现方法,加深对课程的基础理论和算法的理解,加强学生的动手能力。
生产者消费者问题——操作系统课程设计—方案汇报PPT
设计生产者、 消费者数目, 及缓冲区大小
点击开始模拟
观察模拟情况,按需要 调整生产或消费速度 点击分析按钮 查看统计分析数据
退出系统
结构设计(1):
在本模拟系统中,使用者需要设定生产者个数, 消费者个数,期间用户可以选择改变两者的相对速度来进行测试,观察结果是否为 预测结果。最后,使用者还可以点击分析按钮进行实验结果统计分析。
P线程
如果缓冲区不满
缓 冲 区
C线程
P、C线程访问缓 冲区受互斥信号量 mutex控制
如果缓冲区不空
进度安排:
• 寒假期间:确定课题项目,商讨选用何种设计语 言,完成程序框架及基本结构和类的整体设计。 • 2月20日—3月1日:完成设计考核幻灯片的制作, 完成各类方法的编写,完成核心程序并进行基本 测试。 • 3月2日—3月5日:完善核心程序,优化数据结构, 初步进行图形化界面的编写。 • 3月6日—3月10日:完成用户界面程序并进行测试 和改进。完成期间各个总结汇报幻灯片。 • 3月11—结束:综合测试,撰写总结汇报。提交论 文。
创新之处:
• (1)采用Java程序设计语言,其多线程程序设 计可模拟操作系统的并发环境 • (2)用Java中的wait()和notify()来模拟P、V操作 • (3)用进度条和滑动竿比较形象和准确的描述模 拟结果。
“生产者—消费者”问题的模拟系统
操作系统课程设计
目的及意义
通过模拟经典的“生产者—消费者问题”,巩 固在操作系统原理课上所学的知识,加深对操作 系统中实现同步、互斥。并发的方法、临界区管 理等问题的认识和理解,同时了解软件设计的流 程、方法以及思想,提高分析设计以及编程的能 力。
功能设计:
开始界面
操作系统生产者与消费者课程设计
操作系统课程设计课题名称:Windows OS平台下的生产者和消费者问题班级:软件学号:姓名:指导教师:成绩:目录一、课程设计目的 (1)二、课程任务描述 (1)三、技术方案 (1)1. 算法分析 (1)2. 技术机制 (4)3. 库函数介绍 (5)4. 运行环境 (7)四、详细设计 (7)1.程序框架 (8)2.数据结构 (10)3. 流程图 (10)五、运行与测试 (11)六、总结及改进意见 (11)七、附录 (11)一、课程设计目的1.理解生产者消费者模型,掌握基本的同步、互斥算法。
2.理解操作系统中进程间通信机制IPC3.掌握以生产者/消费者模型为依据,在Windows环境下创建一个控制台进程,实现进程(线程)的同步与互斥。
4.掌握和使用共享主存实现进程间通信机制。
二、课程任务描述设计一个C+程序,该程序通过线程并发机制创建两类线程,分别是消费者线程和生产者线程,并运用IPC机制,在Windows平台下,使用信号量和共享内存实现“生产者-消费者”问题。
具体要求:1.使用IPC机制创建信号集,实现”生产者-消费者“问题中的同步与互斥。
2.使用IPC机制创建共享内存,模拟存放产品的公共缓冲区。
3.以生产者/消费者模型为依据,在Windows环境下创建一个控制台进程,在该进程中创建n个线程模拟生产者和消费者,实现进程(线程)的同步与互斥。
三、技术方案1.算法分析1)创建生产者和消费者线程for(i =0;i< (int) n_Thread;i++){if(Thread_Info[i].entity =='P')h_Thread[i]=CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)(Produce),&(Thread_Info[ i]),0,NULL);elseh_Thread[i]=CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)(Consume),& (Thread_Info[i]),0,NULL);}2)生产者进程void Produce(void *p){//局部变量声明;DWORD wait_for_semaphore,wait_for_mutex,m_delay;int m_serial;//获得本线程的信息;m_serial = ((ThreadInfo*)(p))->serial;m_delay = (DWORD)(((ThreadInfo*)(p))->delay *INTE_PER_SEC);Sleep(m_delay);//开始请求生产printf("Producer %2d sends the produce require.\n",m_serial);//确认有空缓冲区可供生产,同时将空位置数empty减1;用于生产者和消费者的同步;wait_for_semaphore = WaitForSingleObject(empty_semaphore,-1);//互斥访问下一个可用于生产的空临界区,实现写写互斥;wait_for_mutex = WaitForSingleObject(h_mutex,-1);int ProducePos = FindProducePosition();ReleaseMutex(h_mutex);//生产者在获得自己的空位置并做上标记后,以下的写操作在生产者之间可以并发;//核心生产步骤中,程序将生产者的ID作为产品编号放入,方便消费者识别;printf("Producer %2d begin to produce at position %2d.\n",m_serial,ProducePos);Buffer_Critical[ProducePos] = m_serial;printf("Producer %2d finish producing :\n ",m_serial);printf(" position[ %2d ]:%3d \n" ,ProducePos,Buffer_Critical[ProducePos]);//使生产者写的缓冲区可以被多个消费者使用,实现读写同步;ReleaseSemaphore(h_Semaphore[m_serial],n_Thread,NULL);}3)消费者进程void Consume(void * p){//局部变量声明;DWORD wait_for_semaphore,m_delay;int m_serial,m_requestNum; //消费者的序列号和请求的数目;int m_thread_request[MAX_THREAD_NUM];//本消费线程的请求队列;//提取本线程的信息到本地;m_serial = ((ThreadInfo*)(p))->serial;m_delay = (DWORD)(((ThreadInfo*)(p))->delay *INTE_PER_SEC);m_requestNum = ((ThreadInfo *)(p))->n_request;for (int i = 0;i<m_requestNum;i++)m_thread_request[i] = ((ThreadInfo*)(p))->thread_request[i];Sleep(m_delay);//循环进行所需产品的消费for(i =0;i<m_requestNum;i++){//请求消费下一个产品printf("Consumer %2d request to consume %2d product\n",m_serial,m_thread_request[i]);//如果对应生产者没有生产,则等待;如果生产了,允许的消费者数目-1;实现了读写同步;wait_for_semaphore=WaitForSingleObject(h_Semaphore[m_thread_request[i]],-1);//查询所需产品放到缓冲区的号int BufferPos=FindBufferPosition(m_thread_request[i]);//开始进行具体缓冲区的消费处理,读和读在该缓冲区上仍然是互斥的;//进入临界区后执行消费动作;并在完成此次请求后,通知另外的消费者本处请求已//经满足;同时如果对应的产品使用完毕,就做相应处理;并给出相应动作的界面提示;该相应处理指将相应缓冲区清空,并增加代表空缓冲区的信号量;EnterCriticalSection(&PC_Critical[BufferPos]);printf("Consumer%2d begin to consume %2d product \n",m_serial,m_thread_request[i]);((ThreadInfo*)(p))->thread_request[i] =-1;if(!IfInOtherRequest(m_thread_request[i])){Buffer_Critical[BufferPos] = -1; //标记缓冲区为空;printf("Consumer%2d finish consuming %2d:\n ",m_serial,m_thread_request[i]);printf(" position[ %2d ]:%3d \n" ,BufferPos,Buffer_Critical[BufferPos]);ReleaseSemaphore(empty_semaphore,1,NULL);}else{printf("Consumer %2d finish consuming product %2d\n ",m_serial,m_thread_request[i]);}//离开临界区LeaveCriticalSection(&PC_Critical[BufferPos]);}}2.技术机制有一个有限缓冲区和多个线程:生产者和消费者。
《操作系统》课程设计说明书_用多线程同步方法解决生产者-消费者问题
目录目录 (1)用多线程同步方法解决生产者-消费者问题 (3)1. 设计题目与要求 (3)1.1设计题目 (3)1.2设计要求 (3)2.设计思想及系统平台 (3)2.1设计思想 (3)2.2系统平台及使用语言 (3)3.数据结构与模块说明 (4)4.源程序清单 (7)5.运行结果与运行情况 (12)6.调试过程.................................................................................................... 错误!未定义书签。
7.总结 (16)本科生课程设计成绩评定表 (18)课程设计任务书学生姓名:专业班级:指导教师:工作单位:计算机科学与技术学院题目: 用多线程同步方法解决生产者-消费者问题 (Producer-Consumer Problem)初始条件:1.操作系统:Linux2.程序设计语言:C语言3.有界缓冲区内设有20个存储单元,其初值为0。
放入/取出的数据项按增序设定为1-20这20个整型数。
要求完成的主要任务:(包括课程设计工作量及其技术要求,以及说明书撰写等具体要求)1.技术要求:1)为每个生产者/消费者产生一个线程,设计正确的同步算法2)每个生产者和消费者对有界缓冲区进行操作后,即时显示有界缓冲区的当前全部内容、当前指针位置和生产者/消费者线程的自定义标识符。
3)生产者和消费者各有两个以上。
4)多个生产者或多个消费者之间须共享对缓冲区进行操作的函数代码。
2.设计说明书内容要求:1)设计题目与要求2)总的设计思想及系统平台、语言、工具等。
3)数据结构与模块说明(功能与流程图)4)给出用户名、源程序名、目标程序名和源程序及其运行结果。
(要注明存储各个程序及其运行结果的主机IP地址和目录。
)5)运行结果与运行情况(提示: (1)有界缓冲区可用数组实现。
(2)编译命令可用:cc -lpthread -o 目标文件名源文件名(3)多线程编程方法参见附件。
生产者消费者问题操作系统课程设计思路
核心技术(2)续——核心函数
public void Signal(Semaphore x_sem,Count x_count,String s2) { frame.a1.append(s2+"执行Signal操作 若当前有等待资源的 线程则唤醒该线程并阻塞自己。否则唤醒信号丢失\n "); if(x_count.Cvalue>0){//判断是否有等待资源的线程 System.out.print("Signal\n"); next_count++;//发出signal操作的线程数加1 x_sem.v(“ 资源可用,唤醒等待资源的线程!! (缓冲 区不满或者不空) 现在\n");//释放一个等待资源的线程 next.p(s2+"线程因发出Signal操作阻塞自己,等待已唤醒的线程 退出管程或其他 事件 \n");//发出signal操作的线程阻塞自己,一旦 阻塞,以下的next_count--;将不会执行,等待被其他管程内部事 件的唤醒。 next_count--;//发出signal操作的线程数减1 } } }
存在的问题
(1)对于进程的追踪和管理尚不到位 ( 2)
(1)对软件开发流程还不熟悉
(2)从理论到实践还有一定程度的困难
改进及讨论
(1)因为应用Java封装好的方法来阻塞和唤醒进程,不 知道其具体实现的方式和管理方式,已经自定义了一个 PCB类尝试跟踪进程,取得一定的效果,但还未完全实现 对其管理与控制。
核心技术(2)续——核心函数
public void Wait(Semaphore x_sem,Count x_count,String s1) { x_count.Cvalue++;//等待资源的线程数加1,初始值为0 System.out.print("Wait\n"); frame.a1.append(s1+"执行Wait操作 因资源不可用而该线程 即将 阻塞自己!! (缓冲区已满或者已为空)\n在阻塞自己之前,先判断是否有发出signal操作的线程。若 有,则释放之。否则准备开放管程。之后便阻塞自己 \n "); if(next_count>0)//判断是否有发出signal操作的线程。因为发出此操作的线程会阻塞自己。 { next.v("释放一个因发出signal操作,唤醒了其他线程而阻塞自己的线程 现在\n");//若 有就释放一个 System.out.print("释放一个发出signal操作的线程\n"); } else { mutex.v("没有因发出signal操作而阻塞自己的线程,也没有当前线程的可用资源 在阻 塞当前线程之前先开放管程,让其他线程有机会获得管程\n");//否则开放管程 System.out.print("开放管程\n"); } x_sem.p(s1+"线程因没有可用资源(即缓冲区)而");///等待资源的线程阻塞自己, X_sem初始化为0 x_count.Cvalue--;//等待资源的线程数减1 }
生产者与消费者的问题-----操作系统课程设计
闽江学院计算机系网络操作系统课程设计设计内容:进程机制与并发程序设计——linux下生产者与消费者的问题实现目录:一、设计内容 (3)二、设计思想 (4)三、系统结构 (5)四、PV操作代码 (5)五、C++程序代码 (6)六、运行结果截图 (9)七、参考文献 (11)八、实验总结 (11)一、设计内容进程机制与并发程序设计————linux下生产者与消费者的问题实现1.实验目的(1)掌握基本的同步互斥算法,理解生产者和消费者同步的问题模型。
(2)了解linux中多线程的并发执行机制,线程间的同步和互斥。
2、实验环境:C/C++语言编译器3、实验要求(1)创建生产者和消费者线程在linux环境下,创建一个控制台进程,在此进程中创建n个线程来模拟生产者或者消费者。
这些线程的信息由本程序定义的“测试用例文件”中予以指定。
该文件的格式和含义如下:31 P 32 P 43 C4 14 P 25 C 3 1 2 4第一行说明程序中设置几个临界区,其余每行分别描述了一个生产者或者消费者线程的信息。
每一行的各字段间用Tab键隔开。
不管是消费者还是生产者,都有一个对应的线程号,即每一行开始字段那个整数。
第二个字段用字母P或者C区分是生产者还是消费者。
第三个字段表示在进入相应线程后,在进行生产和消费动作前的休眠时间,以秒计时;这样做的目的是可以通过调整这一列参数,控制开始进行生产和消费动作的时间。
如果是代表生产者,则该行只有三个字段。
如果代表消费者,则该行后边还有若干字段,代表要求消费的产品所对应的生产者的线程号。
所以务必确认这些对应的线程号存在并且该线程代表一个生产者。
(2)生产和消费的规则在按照上述要求创建线程进行相应的读写操作时,还需要符合以下要求:①共享缓冲区存在空闲空间时,生产者即可使用共享缓冲区。
②从上边的测试数据文件例子可以看出,某一生产者生产一个产品后,可能不止一个消费者,或者一个消费者多次地请求消费该产品。
操作系统生产者与消费者课程设计
一、课程设计的性质与任务1、生产者-消费者问题是很经典很具有代表性的进程同步问题,计算机中的很多同步问题都可抽象为生产者-消费者问题,通过本实验的练习,希望能加深学生对进程同步问题的认识与理解。
2、熟悉VC的使用,培养和提高学生的分析问题、解决问题的能力。
二、课程设计的内容及其要求1.实验内容以生产者/消费者模型为依据,在Windows 2000环境下创建一个控制台进程,在该进程中创建n个线程模拟生产者和消费者,实现进程(线程)的同步与互斥。
2.实验要求●学习并理解生产者/消费者模型及其同步/互斥规则;●学习了解Windows同步对象及其特性;●熟悉实验环境,掌握相关API的使用方法;●设计程序,实现生产者/消费者进程(线程)的同步与互斥;●提交实验报告。
三、课程设计的时间安排课程设计时间8课时四、课程设计的实验环境本实验是在winxp+VC6.0环境下实现的,利用Windows SDK编制实例程序。
所以试验需要在windows下安装VC后进行。
VC是一个集成开发环境,其中包含了Windows SDK所有工具和定义;所以安装了VC后就不用特意安装SDK了。
五、正文1、实验程序的结构图(流程图);开始Wait ProductsWait BufferConsumeProduceWhile consumeWhile produce结束2、数据结构及信号量定义的说明;(1) CreateThread●功能——创建一个在调用进程的地址空间中执行的线程●格式HANDLE CreateThread( LPSECURITY_ATTRIBUTES lpThreadAttributes,DWORD dwStackSize,LPTHREAD_START_ROUTINE lpStartAddress,LPVOID lpParamiter,DWORD dwCreationFlags,Lpdword lpThread );●参数说明lpThreadAttributes——指向一个LPSECURITY_ATTRIBUTES(新线程的安全性描述符)。
生产者消费者问题 操作系统课程设计
生产者消费者问题操作系统课程设计生产者消费者问题是操作系统中常见的一个并发问题,本课程设计旨在帮助学生深入理解该问题及其解决方案。
课程设计内容包括:
1. 生产者消费者问题的定义、特点和解决方案
2. 生产者消费者问题的算法设计与实现
3. 多线程并发编程实践
4. 操作系统调度与同步机制实践
5. 生产者消费者问题的应用场景与案例分析
通过本课程设计,学生将能够掌握操作系统中的重要问题与解决方案,并具备多线程并发编程的实践技能,为以后的操作系统开发与应用打下坚实的基础。
- 1 -。
生产者与消费者的问题操作系统课程设计范本
生产者与消费者的问题操作系统课程设计闽江学院计算机系网络操作系统课程设计设计内容:进程机制与并发程序设计——linux下生产者与消费者的问题实现目录:一、设计内容 (3)二、设计思想 (4)三、系统结构 (5)四、PV操作代码 (5)五、C++程序代码 (6)六、运行结果截图 (9)七、参考文献 (11)八、实验总结 (11)一、设计内容进程机制与并发程序设计————linux下生产者与消费者的问题实现1.实验目的(1)掌握基本的同步互斥算法,理解生产者和消费者同步的问题模型。
(2)了解linux中多线程的并发执行机制,线程间的同步和互斥。
2、实验环境:C/C++语言编译器3、实验要求(1)创立生产者和消费者线程在linux环境下,创立一个控制台进程,在此进程中创立n个线程来模拟生产者或者消费者。
这些线程的信息由本程序定义的“测试用例文件”中予以指定。
该文件的格式和含义如下:31 P 32 P 43 C4 14 P 25 C 3 1 2 4第一行说明程序中设置几个临界区,其余每行分别描述了一个生产者或者消费者线程的信息。
每一行的各字段间用Tab键隔开。
不论是消费者还是生产者,都有一个对应的线程号,即每一行开始字段那个整数。
第二个字段用字母P或者C区分是生产者还是消费者。
第三个字段表示在进入相应线程后,在进行生产和消费动作前的休眠时间,以秒计时;这样做的目的是能够经过调整这一列参数,控制开始进行生产和消费动作的时间。
如果是代表生产者,则该行只有三个字段。
如果代表消费者,则该行后边还有若干字段,代表要求消费的产品所对应的生产者的线程号。
因此务必确认这些对应的线程号存在而且该线程代表一个生产者。
(2)生产和消费的规则在按照上述要求创立线程进行相应的读写操作时,还需要符合以下要求:①共享缓冲区存在空闲空间时,生产者即可使用共享缓冲区。
②从上边的测试数据文件例子能够看出,某一生产者生产一个产品后,可能不止一个消费者,或者一个消费者多次地请求消费该产品。
操作系统课程设计生产者消费者
(操作系统课程设计)生产者和消费者学生姓名:学生学号:班级:0311401、02、03、04班制二〇一三年十二月一、课程题目分析这个题目是生产者向消费者提供商品,消费者消耗商品,并且两组人共用同一缓冲区。
生产者提供了商品之后消费者才能去取商品,消费者若不取走商品则当缓冲区用完之后生产者则不能再向缓冲区中添加新的商品。
思考问题:(1)对于生产者进程:每产生一个数据,则需去访问共用缓冲区是否有已满,未满则可以将该数据存入并通知消费者进程,否则不能。
(2)对于消费者进程:每当想去消费(取出数据)时,则需访问缓冲区是否为空,为空则不能消费(取出数据),否则可以取,并通知生产者。
(3)缓冲区是个临界资源,所有的进程对于该空间都是共享的,所以,还有互斥问题存在。
二、课程设计目的通过实验模拟生产者与消费者之间的关系,了解并掌握他们之间的关系及原理。
由此增加对进程同步问题的了解:(1)掌握基本的同步互斥算法,理解生产者与消费者模型(2)了解windows中多线程(多进程)的并发执行机制,线程(进程)间的同步于互斥(3)学习使用windows中基本的同步对象,掌握相应的API。
三、课程设计内容有n个生产者和m个消费者,连接在具有k个单位缓冲区的有界环转缓冲上,故又称有界缓冲问题。
其中Pi 和Cj都是并发进程,只要缓冲区未满,生产者进程Pi 所生产的产品就可投入缓冲区;类似地,只要缓冲区非空,消费者进程Cj就可以从缓冲区取走并消耗产品。
四、开发环境操作系统:Windows系统编写语言:C++语言五、系统分析设计(一)算法原理生产者——消费者问题是典型的进程同步问题,这些进程必须按照一定的生产率和消费率来访问共享缓冲区,用P、V操作解决生产者和消费者共享单缓冲区的问题,可设置两个信号量empty和full,其初值分别为1和0,empty指示能否向缓冲区放入产品,full指示能否从缓冲区取出产品。
为了使其协调工作,必须使用一个信号量mutex(初值为1),以限制生产者和消费者互斥地对缓冲区进行存取,另用两个信号量empty1(初值为缓冲区大小)和full1(初值为0),以保证生产者不向已满的缓冲区中放入产品,消费者不从空缓冲区中取产品。
生产者消费者_操作系统课程设计[1]
利用管程解决“生产者—消费者”问题摘要:现代操作系统引入并发程序设计技术之后,程序的执行不再是顺序的,封闭的。
在多个进程并发运行的过程中,进程之间可能产生相互制约的关系,即竞争和协作。
为了协调各进程有序正确的进行,就需要各进程间能相互通信。
如果各进程之间不加以来控制,就会产生错误,如与时间有关的错误等。
这就需要考虑进程之间的同步和互斥等问题。
操作系统中经典的“生产者—消费者”问题正反映了进程并发执行的这种关系。
本课程设计所完成的就是对“生产者—消费者”问题的模拟,本系统根据操作系统中并发进程、临界区、同步和互斥等基本概念及理论进行设计,采用Java语言实现,用管程来对进程进行模拟同步和互斥的控制。
本系统可按照用户设定的生产者消费者数目及缓冲区大小来进行模拟演示。
这对深入理解操作系统中进程的同步和互斥问题,探求对进程控制方法的学习上有重大意义。
关键字:管程;进程同步;进程互斥;临界资源1.研究目的及意义本课程设计通过模拟计算机操作系统中经典的“生产者—消费者问题”,巩固在操作系统原理课上所学的知识,加深对操作系统中进程同步和互斥、临界区管理,管程等问题的认识和理解。
前期主要利用P、V信号量来控制各进程间的同步于互斥关系,确保各进程有序正确的进行。
然而,我们也知道,使用信号量和P、V操作在实现进程同步时,对共享资源的管理分散于各个进程中,进程能够直接对共享变量进行处理,不利于系统对系统资源的管理,容易造成程序设计错误。
因此,在后期我们改用管程来实现,目的是想把资源集中起来统一管理,即把相关的共享变量及其操作集中在一起统一的控制和管理,使各并发进程间的相互作用更为清晰。
当然,我们本次课程设计也为我们了解软件设计的流程、方法以及思想,提高分析设计以及编程的能力提供了基础。
2.理论基础及分析2.1问题的引入在操作系统引入并发程序设计技术之后,程序的执行不再是顺序和封闭的,程序外部的顺序特性消失,程序与计算不再一一对应。
消费者生产者问题计算机操作系统课程设计
齐齐哈尔大学操作系统课程综合实践题目:多进程同步方法解决生产者一消费者问题班级:__0 ________________________姓名:__0 ________________________学号:__0 __________________指导教师:__0 ____________________2011 年12月7日综合实践评分表A CBCD E总分在90〜100为优,80〜89为良,70〜79为中,60〜69为及格,60分以下为不及格。
多进程同步方法解决生产者-消费者问题摘要:本文论述了多进程同步方法解决生产者-消费者问题的过程。
该程序使学生对操作系统的工作机制有了初步的了解,其主要目的是使学生了解和撑握在Linux 系统平台下的 C 语言编程,用来解决实现生活中遇到的问题。
并以Linux 系统开发平台,以及虚拟机来实现。
关键字:生产者-消费者问题,Linux 系统平台,虚拟机,信号量,线程(thread)多进程同步方法解决生产者-消费者问题一、课程设计所需设备计算机一台,Red Hat linux9.03 系统一套。
二、课程设计预期目的通过研究Linux 的进程机制和信号量实现生产者消费者问题的并发控制。
三、课程设计任务用多进程同步方法解决生产者- 消费者问题设计目的: 通过研究Linux 的进程机制和信号量实现生产者消费者问题的并发控制.说明: 有界缓冲区内设有20 个存储单元, 放入/ 取出的数据项设定为1-20 这20 个整型数.设计要求:1)每个生产者和消费者对有界缓冲区进行操作后, 即时显示有界缓冲区的全部内容, 当前指针位置和生产者/消费者线程的标识符.2)生产者和消费者各有两个以上.3)多个生产者或多个消费者之间须有共享对缓冲区进行操作的函数代码.四、课程设计基本思想多进程是一种非常简洁的多任务操作方式。
在Linux 系统下,启动一个新的进程必须分配给它独立的地址空间,建立众多的数据表来维护它的代码段、堆栈段和数据段,这是一种烦琐的多任务工作方式。
操作系统课程设计-管程的实现(生产者消费者问题)
操作系统课程设计2、管程的实现(生产者消费者问题)1.设计背景:管程是一种高级抽象数据类型,它支持在它的函数中隐含互斥操作。
结合条件变量和其他一些低级通信原语,管程可以解决许多仅用低级原语不能解决的同步问题。
例如,本实验中利用管程提供一个不会发生死锁的生产者消费者问题就是利用管程的很好的例子。
管程封装了并发进程或线程要互斥执行的函数。
为了让这些并发进程或线程在管程内互斥的执行,管程的实现必须隐含的具有锁或二值信号量。
如果没有条件变量,管程就不会有很有用,条件变量提供了一种对管程内并发协作进程的同步机制。
条件变量代表了管程中一些并发进程或线程可能要等待的条件。
一个条件变量管理着管程内的一个等待队列。
如果管程内某个进程或线程发现其执行条件为假,则该进程或线程就会被条件变量挂入管程内等待该条件的队列。
如果管程内另外的进程或线程满足了这个条件,则它会通过条件变量再次唤醒等待该条件的进程或线程,从而避免了死锁的产生。
所以,一个条件变量C应具有两种操作 C.wait()和C.signal()。
当管程内同时出现唤醒者和被唤醒者时,由于要求管程内的进程或线程必须互斥执行,因此就出现了两种样式的条件变量:Mesa Style(signal-and-continue): 唤醒者进程或线程继续执行,被唤醒者进程或线程等到唤醒者进程或线程阻塞或离开管程后再执行。
Hoare Style(signal-and-wait): 被唤醒者进程或线程立即执行,唤醒者进程或线程阻塞,直道被唤醒者阻塞或离开管程后再执行。
我们实验所做的就是在原来mesa样式的基础上进行Hoare样式的改进;这种样式也是我们实验中需要实现的样式。
2.设计目标验证并分析Nachos中Bridge管程是否能够正确的解决单行桥双向过桥问题。
定义和实现Hoare样式的条件变量Condition_H类利用Hoare样式的条件变量Condition_H,实现Ring类中定义的各个方法,使用Ring管程解决生产者/消费者问题。
生产者消费者问题_______操作系统课程设计报告
.课程设计报告课程名称:Linux操作系统专业计算机科学与技术学生XX班级学号指导教师完成日期信息工程学院题目:生产者-消费者问题的模拟实现一、设计目的本课程设计是学习完“操作系统原理〞课程后进展的一次全面的综合训练,通过课程设计,更好地掌握操作系统的原理及实现方法,加深对操作系统根底理论和重要算法的理解,加强学生的动手能力。
二、设计内容〔1〕概述设计目的:通过研究Linux的进程机制和信号量实现生产者消费者问题的并发控制。
说明:有界缓冲区内设有20个存储单元,放入/取出的数据项设定为1-20这20个整型数。
设计要求:(1)每个生产者和消费者对有界缓冲区进展操作后,即时显示有界缓冲区的全部内容,当前指针位置和生产者/消费者县城的标识符。
(2)生产者和消费者各有两个以上。
(3)多个生产者或多个消费者之间须有共享对缓冲区进展操作的函数代码。
〔2〕设计原理通过一个有界缓冲区把生产者和消费者联系起来。
假定生产者和消费者的优先级是一样的,只要缓冲区未满,生产者就可以生产产品并将产品送入缓冲区。
类似地,只要缓冲区未空,消费者就可以从缓冲区中取走产品。
应该制止生产者向满的缓冲区送入产品,同时也应该制止消费者从空的缓冲区中取出产品,这一机制有生产者线程和消费者线程之间的互斥关系来实现。
与计算打印两进程同步关系一样,生产者和消费者两进程P和C之间应满足以下两个同步条件:①只有在缓冲池中至少有一个缓冲区已存入消息后,消费者才能从中提取信息,否那么消费者必须等待。
②只有缓冲池中至少有一个缓冲区是空时,生产者才能把消息放入缓冲区,否那么生产者必须等待。
为了满足第一个同步条件,设置一个同步信号量full,它代表的资源是缓冲区满,它的初始值为0,它的值为n时整个缓冲池满。
这个资源是消费者类进程C所有,C进程可以申请该资源,对它施加P操作,而C进程的合作进程生产者进程P对它施加V 操作。
同样为了满足第二个同步条件,设置另一个同步信号量empty,它代表的资源是缓冲空区,它的初始值为n,表示缓冲池中所有缓冲区空。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
课程设计报告课程名称:操作系统专业____________ 计算机科学与技术__________ 学生姓名____________________________________ 班级_______________________________________ 学号_______________________________________ 指导教师____________________________________ 完成日期___________________________________信息工程学院题目:生产者-消费者问题的模拟实现一、设计目的本课程设计是学习完“操作系统原理”课程后进行的一次全面的综合训练,通过课程设计,更好地掌握操作系统的原理及实现方法,加深对操作系统基础理论和重要算法的理解,加强学生的动手能力。
二、设计内容(1)概述设计目的:通过研究Linux的进程机制和信号量实现生产者消费者问题的并发控制。
说明:有界缓冲区内设有20个存储单元,放入/取出的数据项设定为1-20这20个整型数。
设计要求:(1)每个生产者和消费者对有界缓冲区进行操作后,即时显示有界缓冲区的全部内容,当前指针位置和生产者/消费者县城的标识符。
(2)生产者和消费者各有两个以上。
(3)多个生产者或多个消费者之间须有共享对缓冲区进行操作的函数代码。
(2)设计原理通过一个有界缓冲区把生产者和消费者联系起来。
假定生产者和消费者的优先级是相同的,只要缓冲区未满,生产者就可以生产产品并将产品送入缓冲区。
类似地,只要缓冲区未空,消费者就可以从缓冲区中取走产品。
应该禁止生产者向满的缓冲区送入产品,同时也应该禁止消费者从空的缓冲区中取出产品,这一机制有生产者线程和消费者线程之间的互斥关系来实现。
与计算打印两进程同步关系相同,生产者和消费者两进程P和C之间应满足下列两个同步条件:①只有在缓冲池中至少有一个缓冲区已存入消息后,消费者才能从中提取信息,否则消费者必须等待。
②只有缓冲池中至少有一个缓冲区是空时,生产者才能把消息放入缓冲区,否则生产者必须等待。
为了满足第一个同步条件,设置一个同步信号量full,它代表的资源是缓冲区满,它的初始值为0,它的值为n时整个缓冲池满。
这个资源是消费者类进程C所有,C进程可以申请该资源,对它施加P操作,而C进程的合作进程生产者进程P对它施加V操作。
同样为了满足第二个同步条件,设置另一个同步信号量empty,它代表的资源是缓冲空区,它的初始值为n,表示缓冲池中所有缓冲区空。
信号量full表示可用缓冲区数量,信号量empty表示缓冲区数量,设置整型变量:存入指针in和取出指针out。
为解决生产者/消费者问题,应该设置两个资源信号量,其中一个表示空缓冲区的数目,用g_hFullSemaphore表示,其初始值为有界缓冲区的大小SIZE_OF_BUFFEF另一个表示缓冲区中产品的数目,用g_hEmptySemaphore表示,其初始值为0.另外,由于有界缓冲区是一个临界资源,必须互斥使用,所以还需要在设置一个互斥信号量g_hMutex,初始值为1.P原语的主要动作是:①sem减1 ;②若sem减一后仍大于或等于零,则进程继续执行;③若sem减一后小于零,则该进程被阻塞后入与该信号相对应的队列中,然后转进程调度。
V原语的操作主要动作是:①sem加1 ;②若相加结果大于零,进程继续执行;③若相加结果小于或等于零,则从该信号的等待队列中唤醒一等待进程然后再返回原进程继续执行或转进程调度。
采用的同步方法:1)利用函数CreateMutex(NULL,FALSE,NULL创建互斥信号量g_hMutex,表示缓冲区当前的状态,若为true时,则表示缓冲区正被别的进程使用。
三个参数表示的意义分别为:指向安全属性的指针,初始化互斥对象的所有者,指向互斥对象名的指针。
2)利用函数CreateSemaphore(NULL,SIZE_OF_BUFFER-1,SIZE_OF_BUFFER-1, NULL创建缓冲区满的信号量g_hFullSemaphore,值为true时表示缓冲区已满。
四个参数分别为:表示是否允许继承、设置信号机的初始计数、设置信号机的最大计数、指定信号机对象的名称(-1是因为计数从开始)。
3) 利用函数CreateSemaphore(NULL,0,SIZE_OF_BUFFER-1,NUL创建缓冲区空的信号量g_hEmptySemaphore该值为true时表示缓冲区为空。
5、数据定义及其详细解释const un sig ned short SIZE_OF_BUFFER = 20; //DWORD WINAPI Producer(LPVOID); //DWORD WINAPI Con sumer(LPVOID); // 消费者线程(3)详细设计及编码流程图缓冲区长度un sig ned s hort ProductID = 0; // un sig ned s hort Co nsumelD = 0; // un sig ned s hort in = 0; //un sig ned s hort out = 0; //int g_buffer[SIZE_OF_BUFFER]; // bool g_continue = true; //HANDLE g_hMutex; // HANDLE g_hFullSemaphore; // HANDLE g_hEmptySem aphore; //产品号将被消耗的产品号产品进缓冲区时的缓冲区下标产品出缓冲区时的缓冲区下标缓冲区是个循环队列使程序跳出循环,控制程序结用于线程间的互斥当缓冲区满时迫使生产者等待当缓冲区空时迫使消费者等待生产者线程消费者:程序清单1. 存储结构定义利用信号量解决生产者消费者问题const un sig ned shortSIZE_OF_BUFFER = 10; // 缓冲区长度 un sig ned short ProductID = 0;//un sig ned short Con sumeID = 0; // un sig ned short in = 0; // un sig ned short out = 0; //in tg_buffer[SIZE_OF_BUFFER]; bool g_continue = true; // HANDLE g_hMutex;HANDLE g_hFullSem aphore; // HANDLE g_hEmptySem aphore; //DWORD WINAPI Producer(LPVOID); // 生产者线程 DWORD WINAPI Con sumer(LPVOID); // 消费者线程 2. 算法相关的函数(1)创建各个互斥信号以及生产者线程和消费者线程的函数在如下主函数里面 所示:产品号将被消耗的产品号产品进缓冲区时的缓冲区下标 产品出缓冲区时的缓冲区下标 缓冲区是个循环队列控制程序结束 用于线程间的互斥当缓冲区满时迫使生产者等待 当缓冲区空时迫使消费者等待// //入口int main(){//创建各个互斥信号g_hMutex = CreateMutex(NULL,FALSE,NULL);g_hFullSemaphoreCreateSemaphore(NULL,SIZE_OF_BUFFER-1,SIZE_OF_BUFFER-1,NULL);g_hEmptySemaphore = CreateSemaphore(NULL,0,SIZE_OF_BUFFER-1,NULL); //调整下面的数值,可以发现,当生产者个数多于消费者个数时,//生产速度快,生产者经常等待消费者;反之,消费者经常等待。
const un sig ned short PRODUCERS_COUNT = 3; // 生产者的个数const un sig ned short CONSUMERS_COUNT = 1; // 消费者的个数//总的线程数const un sig ned short THREADS_COUNTPRODUCERS_COUNT+CONSUMERS_COUNT;HANDLE hThreads[PRODUCERS_COUNT]; // 各线程的handleDWORD producerID[CONSUMERS_COUNT]; // 生产者线程的标识符DWORD con sumerlD[THREADS_COUNT]; // 消费者线程的标识符// 创建生产者线程for (i nt i=0;i {hThreads[i]=CreateThread(NULL,0,Producer,NULL,0,&producerlD[i]);if (hThreads[i]==NULL)return -1;}//创建消费者线程for ( i=0;i {hThreads[PRODUCERS_COUNT+i]=CreateThread(NULL,0,Co nsumer,NULL,0 &con sumerID[i]);if (hThreads[i]==NULL)return -1;}while(g_co nti nue){if(getchar()){ // 按回车后终止程序运行g_continue = false; }}return 0; }(2)生产者生产一个产品的函数://生产一个产品。
简单模拟了一下,仅输出新产品的voidID号Produce。
{std::cerr << "Producing " << ++ProductlD << " *** "; std::cerr << "Succeed" << std::e ndl;}(3)把新生产的产品放入缓冲区的函数://把新生产的产品放入缓冲区void Appe nd(){std::cerr << "Appe nding a product *** ";g_buffer[i n] = ProductID;in = (in+1)%SIZE_OF_BUFFER;std::cerr << "Succeed" << std::e ndl;}(4)输出缓冲区当前的状态的函数://输出缓冲区当前的状态for (i nt i=0;i {std::cout << i <<": " << g_buffer[i];if (i==in)std::cout << " <-- 生产";if (i==out)std::cout << " <-- 消费";std::cout << std::e ndl;}从缓冲区中取出一个产品的函数://从缓冲区中取出一个产品void Take(){std::cerr << "Tak ing a product *** ";Con sumelD = g_buffer[out];out = (out+1)%SIZE_OF_BUFFER;利用信号量解决生产者消费者问题std::cerr << "Succeed" << std::e ndl;}(5)输出缓冲区当前的状态的函数:// 输出缓冲区当前的状态for (i nt i=0;i {std::cout << i <<": " << g_buffer[i];if (i==in)std::cout << " <-- 生产";if (i==out)std::cout << " <-- 消费";std::cout << std::e ndl;}}(6)消耗一个产品的函数://消耗一个产品void Con sume(){std::cerr << "Consuming " << ConsumelD << " *** "; std::cerr << "Succeed" << std::e ndl;}3. 生产者和消费者算法(1)生产者算法://生产者DWORD WINAPI Producer(LPVOID IpPara){while(g_co nti nue){WaitForSi ngleObject(g_hFullSemaphore,INFINITE);WaitForSi ngleObject(g_hMutex,INFINITE); Produce();Appe nd();Sleep(1500);ReleaseMutex(g_hMutex);ReleaseSemaphore(g_hEmptySemaphore,1,NULL);}return 0;}(2)消费者算法://消费者DWORD WINAPI Co nsumer(LPVOID IpPara){while(g_co nti nue){WaitForSi ngleObject(g_hEmptySem aphore,INFINITE);WaitForSi ngleObject(g_hMutex,INFINITE);Take();Con sume();Sleep(1500);ReleaseMutex(g_hMutex);ReleaseSemaphore(g_hFullSemaphore,1,NULL);}return 0;}(4)运行结果分析•' C:\U5er5\zhoul ijia niXDocu ments\C - F ree\T 吕m p\未命窖L EZKE *■ ' C:\U sersVhou li p 'i.an^ E>DOJ ments\C- FreeM Firps 未命容 倍B 〈—生产® ePruduulnji]) 19 ■ ■ - Succeedl^ppendin'Q a product ... Succeed1回1 2 3 4 5 & 7 8 9 o 1 11111 1- 1 1-0 9 1 I;■■■■■■■■ ■■-二-■■ ■■ ■■ 0 123 4 5 6 7 8 9 0 S3Li7' “Q:\U^ers\znouFijian\DocumentAC-Free\TemE未肖呂l.exe*输入输出数据说明和分析:该程序设置的缓冲区数据长度为20,生产者个数为3,消费者个数为1,程序启动后,生产者先进行生产,当3个生产者全部生产完之后,消费者开始从缓冲区中取出产品,当消费者取出一个后,生产者开始继续生产,当生产完3个之后,消费者开始从缓冲池中取产品,依次循环。