




版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
理发师问题:一个理发店由一间等候室W和一间工作室B组成。顾客可以从外面大街上进入W等候理发。两个房间的入口是并排的,且共享一扇日本式可滑动的推拉门(门总是挡住一个入口)。顾客在工作室内理完发,可由B的旁门出去。W中有N把椅子,顾客必须坐着等候。理发师可由门上小窗查看W中无人就睡觉,否则开门,并叫一位顾客入内理发。顾客每进入一位,都拉铃通知理发师。若把顾客和理发师都视为进程,请用P、V操作写出进程的同步算法。要求打印:题目中要求描述理发师和顾客的行为,因此需要两类线程barber()和customer()分别描述理发师和顾客的行为。其中,理发师有活动有理发和睡觉两个事件;等待和理发二个事件。店里有固定的椅子数,上面坐着等待的顾客,顾客在到来这个事件时,需判断有没有空闲的椅子,理发师决定要理发或睡觉时,也要判断椅子上有没有顾客。所以,顾客和理发师之间的关系表现为:(1)理发师和顾客之间同步关系:当理发师睡觉时顾客近来需要唤醒理发师为其理发,当有顾客时理发师为其理发,没有的时候理发师睡觉。(2)理发师和顾客之间互斥关系:由于每次理发师只能为一个人理发,且可供等侯的椅子有限只有n把,即理发师和椅子是临界资源,所以顾客之间是互斥的关系。(3)故引入3个信号量和一个控制变量:ⅰ控制变量waiting用来记录等候理发的顾客数,初值为0;ⅱ信号量customers用来记录等候理发的顾客数,并用作阻塞理发师进程,初值为0;ⅲ信号量barbers用来记录正在等候顾客的理发师数,并用作阻塞顾客进程,初值为1;ⅳ信号量mutex用于互斥,初值为1usingSystem;usingSystem.Collections.Generic;usingSystem.Text;usingSystem.Threading;namespace理发师问题2{internalclassProgram{//FieldsprivatestaticSemaphorebarbers=newSemaphore(1,10);privatestaticintchairs;privatestaticintcount=0;privatestaticSemaphorecustomers=newSemaphore(0,10);privatestaticintfinish=0;privatestaticSemaphoremtx=newSemaphore(1,10);privatestaticintwaiting=0;//Methodspublicstaticvoidbarber(){while(true){customers.WaitOne();mtx.WaitOne();waiting--;barbers.Release();mtx.Release();cuthair();finish++;}}publicstaticvoidcustomer(){mtx.WaitOne();count++;Console.WriteLine("叮咚!第{0}个顾客来了",count);if(waiting<chairs){if(waiting>0){Console.WriteLine("此时有{0}个人在等待理发",waiting);}else{Console.WriteLine("没有人在等待");}waiting++;Console.WriteLine("还有{0}个座位,顾客留下",(chairs-waiting)+1);mtx.Release();customers.Release();barbers.WaitOne();gethaircut();}else{Console.WriteLine("座位已满,第{0}个顾客离开",count);mtx.Release();}}publicstaticvoidcuthair(){Console.WriteLine("开始理发!这是理发师的第{0}个顾客.",finish+1);Thread.Sleep(0x2328);Console.WriteLine("理发完成!");}publicstaticvoidgethaircut(){Thread.Sleep(0x238c);Console.WriteLine("第{0}个顾客理发完毕,离开.",finish);}privatestaticvoidMain(string[]args){stringstr=string.Empty;Console.WriteLine("请输入椅子的总数目:");chairs=Convert.ToInt32(Console.ReadLine());Console.WriteLine("理发店共有{0}把椅子",chairs);Console.WriteLine("开门接待顾客吗?Y/N");for(stringstr2=Console.ReadLine();(str2!="Y")&&(str2!="y");str2=Console.ReadLine()){Console.WriteLine("********对不起,尚未开门!********");Console.WriteLine("开门接待顾客吗?Y/N");}Console.WriteLine("********营业中,欢迎光临!********");newThread(newThreadStart(Program.barber)).Start();while((str!="y")&&(str!="Y")){Randomrandom=newRandom(DateTime.Now.Millisecond);Thread.Sleep(random.Next(1,0x2710));Console.WriteLine("*******************************");newThread(newThreadStart(Program.customer)).Start();if((finish>=10)&&(waiting==0)){Console.WriteLine("已经为{0}个顾客理发了,要关门下班吗?(Y/N)",finish);str=Console.ReadLine();}if((str=="Y")||(str=="y")){Console.WriteLine("************暂停营业!**********");break;}}}}}题目:用多线程同步方法解决睡眠理发师问题(Sleeping-BarberProblem)理发店有一位理发师,一把理发椅和n把用来等候理发的椅子。如果没有顾客,则更好师便在理发椅上睡觉,顾客到来时,如理发师闲则理发,否则如有空等候椅则坐等,没有空椅则离开,编写程序实现理发师和顾客程序,实现进程控制,要求不能出现竞争。2.将1题中问题修改为有两位理发师,设计程序实现同步控制。问题提示:可以用一个变量waiting来记录等候理发的顾客数,另使用三个信号量:用来记录等候理发的顾客数customers;用来记录理发师是否空闲的信息号量barbers,一个用于互斥访问waiting变量的mutex。1已经做好了,只是想把理发师扩充问两个,求助!初始条件:操作系统:Linux程序设计语言:C语言3.设有一个理发师,5把椅子(另外还有一把理发椅),几把椅子可用连续存储单元。要求完成的主要任务:(包括课程设计工作量及其技术要求,以及说明书撰写等具体要求)1.技术要求:1)为每个理发师/顾客产生一个线程,设计正确的同步算法2)每个顾客进入理发室后,即时显示“Entered”及其线程自定义标识,还同时显示理发室共有几名顾客及其所坐的位置。3)至少有10个顾客,每人理发至少3秒钟。4)多个顾客须共享操作函数代码。2.设计说明书内容要求:1)设计题目与要求2)总的设计思想及系统平台、语言、工具等。3)数据结构与模块说明(功能与流程图)4)给出用户名、源程序名、目标程序名和源程序及其运行结果。(要注明存储各个程序及其运行结果的主机IP地址和目录。)5)运行结果与运行情况(提示: (1)连续存储区可用数组实现。(2)编译命令可用:cc-lpthread-o目标文件名源文件名(3)多线程编程方法参见附件。)1设计题目与要求1.1设计题目用多线程同步方法解决睡眠理发师问题(Sleeping-BarberProblem)1.2设计要求1.2.1初始条件(1)操作系统:Linux(2)程序设计语言:C语言(3)设有一个理发师,5把椅子(另外还有一把理发椅),几把椅子可用连续存储单元。1.2.2技术要求(1)为每个理发师/顾客产生一个线程,设计正确的同步算法(2)每个顾客进入理发室后,即时显示“Entered”及其线程自定义标识,还同时显示理发室共有几名顾客及其所坐的位置。(3)至少有10个顾客,每人理发至少3秒钟。(4)多个顾客须共享操作函数代码。2总体设计思想及开发环境与工具2.1总体设计思想题目中要求描述理发师和顾客的行为,因此需要两类线程barber()和customer()分别描述理发师和顾客的行为。其中,理发师有活动有理发和睡觉两个事件;等待和理发二个事件。店里有固定的椅子数,上面坐着等待的顾客,顾客在到来这个事件时,需判断有没有空闲的椅子,理发师决定要理发或睡觉时,也要判断椅子上有没有顾客。所以,顾客和理发师之间的关系表现为:(1)理发师和顾客之间同步关系:当理发师睡觉时顾客近来需要唤醒理发师为其理发,当有顾客时理发师为其理发,没有的时候理发师睡觉。(2)理发师和顾客之间互斥关系:由于每次理发师只能为一个人理发,且可供等侯的椅子有限只有n把,即理发师和椅子是临界资源,所以顾客之间是互斥的关系。(3)故引入3个信号量和一个控制变量:ⅰ控制变量waiting用来记录等候理发的顾客数,初值为0;ⅱ信号量customers用来记录等候理发的顾客数,并用作阻塞理发师进程,初值为0;ⅲ信号量barbers用来记录正在等候顾客的理发师数,并用作阻塞顾客进程,初值为1;ⅳ信号量mutex用于互斥,初值为12.2多线程编程原理此次在Linux下进行多线程编程需要用到pthread_create和pthread_join这两个函数。2.2.1创建一个线程pthread_create用来创建一个线程,原型为:externintpthread_create((pthread_t*__thread,__constpthread_attr_t*__attr,void*(*__start_routine)(void*),void*__arg))第一个参数为指向线程标识符的指针,第二个参数用来设置线程属性,第三个参数是线程运行函数的起始地址,最后一个参数是运行函数的参数。函数thread不需要参数时,最后一个参数设为空指针。第二个参数设为空指针时,将生成默认属性的线程。创建线程成功后,新创建的线程则运行参数三和参数四确定的函数,原来的线程则继续运行下一行代码。2.2.2等待一个线程结束pthread_join用来等待一个线程的结束,函数原型为:externintpthread_join__P((pthread_t__th,void**__thread_return));
第一个参数为被等待的线程标识符,第二个参数为一个用户定义的指针,它可以用来存储被等待线程的返回值。这个函数是一个线程阻塞的函数,调用它的函数将一直等待到被等待的线程结束为止,当函数返回时,被等待线程的资源被收回。2.2.3信号量(1)函数sem_init()用来初始化一个信号量,函数原型为:externintsem_init__P((sem_t*__sem,int__pshared,unsignedint__value));sem为指向信号量结构的一个指针;pshared不为0时此信号量在进程间共享,否则只能为当前进程的所有线程共享;value给出了信号量的初始值。(2)函数sem_post(sem_t*sem)用来增加信号量的值。当有线程阻塞在这个信号量上时,调用这个函数会使其中的一个线程不在阻塞,选择机制同样是由线程的调度策略决定的。(3)函数sem_wait(sem_t*sem)被用来阻塞当前线程直到信号量sem的值大于0,解除阻塞后将sem的值减一,表明公共资源经使用后减少。函数sem_trywait(sem_t*sem)是函数sem_wait()的非阻塞版本,它直接将信号量sem的值减一。2.3伪码实现difinen5;//为顾客准备的椅子数为5semaphoremutex=1;//用于互斥semaphorecustomers=0;//等候理发的顾客数semaphorebarbers=1;//正在等候顾客的理发师数intwaiting=0;//等候理发的顾客数//理发师线程voidbarber(){while(true)//判断有无顾客{wait(customers);//若无顾客,理发师睡眠wait(mutex);//互斥waiting--;//等候顾客数少一个signal(mutex);//释放临界资源signal(barber);//理发师去为一个顾客理发cut_hair;//正在理发}}//顾客线程voidcustomer(){wait(mutex);//互斥if(waiting<n)//如果有空椅子,则等待{waiting++;//等候顾客数加1signal(mutex);//释放临界资源signal(customers);//如果理发师睡觉,唤醒理发师wait(barber);//理发师在理发,顾客等候get_haircut;//顾客坐下等理发师}elsesignal(mutex);//店里人满了,顾客离开}}2.4开发环境与工具系统平台:LINUX环境实现语言:C语言开发工具:NANO编辑器3数据结构与模块说明3.1数据结构通过分析课程设计要求,定义以下的数据:sem_tmutex,customers,barbers;//designthreesemaphores:mutex,customer,barbersintwaiting=0;//thenumberofwaitingcustomersintchair[5];3.2程序模块说明3.2.1主函数模块主函数流程图如下:3.2.2理发师模块理发师模块函数流程图如下:3.2.3顾客模块顾客模块函数流程图如下:源程序代码#include<stdio.h>#include<stdlib.h>#include<unistd.h>#include<pthread.h>#include<semaphore.h>#include<fcntl.h>#include<errno.h>#definen5//theshophavefivechairs//designthreesemaphores:mutex,customer,barberssem_tmutex,customers,barbers;intwaiting=0;//thenumberofwaitingcustomersintchair[5];void*barber();void*customer(void*arg);intmain(intargc,char*argv[]){//create10semaphoresandoneBarbersemaphorepthread_tCustomer_id[10],Barber_id;inti;sem_init(&mutex,0,1);//initmutexsemaphoreto1sem_init(&customers,0,0);//initsemaphorecustomersto0sem_init(&barbers,0,1);for(i=0;i<5;i++)pthread_create(&Barber_id,NULL,(void*)barber,NULL);for(i=0;i<10;i++)pthread_create(&Customer_id[i],NULL,(void*)customer,(void*)(i+1));for(i=0;i<10;i++)pthread_join(Customer_id[i],NULL);for(i=0;i<5;i++)pthread_join(Barber_id,NULL);return0;}//creatbarberpthreadvoid*barber(){inti;intnext;//wait(customers),ifnocustomers,barbersleepingsem_wait(&customers);sem_wait(&mutex);//wait(mutex)waiting--;//thenumerofwaitingreduceonefor(i=0;i<5;i++){if(chair[i]!=0){next=chair[i];chair[i]=0;break;}}printf("Thebarberiscutting%dthcustomer'shair\n",next);sleep(3);sem_post(&mutex);sem_post(&barbers);}//creatcustomerpthreadvoid*customer(void*arg){inti;sem_wait(&mutex);//wait(mutex)if(waiting<n)if(waiting<n){waiting++;//thenumerofwaitingplusonefor(i=0;i<5;i++){if(chair[i]==0){chair[i]=(int)arg;break;}}printf("***************************************************\n");printf("Entered:Number%dcustomercomes,andsitsat%dchair\n",(int)arg,(i+1));printf("Thereare%dcustomeronthechair\n",waiting);printf("Thecustomers'locationare:");for(i=0;i<5;i++)printf("%d",chair[i]);pri
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 肝性脑病护理
- 成人有创机械通气气道内吸引技术操作护理团标解读
- 情绪管理报告范文
- 二零二五年度智能交通系统客户引荐提成协议
- 二零二五年度机关炊事员健康体检聘用合同
- 美容美发店员工入股分红及管理权移交合同(2025年)
- 二零二五年度生物医药产业抵押贷款合同
- 二零二五年度跨境运输汽车指标租赁管理协议
- 二零二五年度家庭房产赠与及后续维护服务合同
- 二零二五年度航空航天知识产权使用授权合同
- 小学生寒假生活成长册PPT
- GB/T 25775-2010焊接材料供货技术条件产品类型、尺寸、公差和标志
- 全省检察机关公诉业务知识考试试卷
- 10KV开关柜教学讲解课件
- 损伤疼痛病(软组织损伤)中医临床路径
- 航模队第一讲-飞机基本原理和弹射机制作
- 花城版三年级下册音乐教学计划
- 全国计算机等级证书样本
- 说明书-prsPRS-7177电能质量监测装置
- 知名房地产抖音代运营方案
- ISO 9001:2015新版质量管理体系详解与案例文件汇编
评论
0/150
提交评论