您好,欢迎访问三七文档
课程设计采用“写优先”策略的“读者-写者”问题学号:20101202014姓名:孔方圆专业:计算机科学与技术指导教师:爱新觉罗日期:2013年3月22日2一、设计目的与内容课程设计的目的:操作系统课程设计是计算机专业重要的教学环节,它为学生提供了一个既动手又动脑,将课本上的理论知识和实际有机的结合起来,独立分析和解决实际问题的机会。※进一步巩固和复习操作系统的基础知识。※培养学生结构化程序、模块化程序设计的方法和能力。※提高学生调试程序的技巧和软件设计的能力。※提高学生分析问题、解决问题以及综合利用C语言进行程序设计的能力。设计内容:用高级语言编写和调试一个采用“写优先”策略的“读者-写者”问题的模拟程序。设计要求:1.读者与写者至少包括ID、进入内存时间、读写时间三项内容,可在界面上进行输入2.读者与写者均有二个以上,可在程序运行期间动态增加读者与写者3.可读取样例数据(要求存放在外部文件中),进行读者/写者、进入内存时间、读写时间的初始化34.要求将运行过程用可视化界面动态显示,可随时暂停,查看阅览室中读者/写者数目、读者等待队列、写者等待队列、读写时间、等待时间5.读写策略为:读写互斥、写写互斥、写优先(只要写者到达,就阻塞后续的所有读者,一旦阅览室无人,写者能最快进入阅览室;在写者未出阅读室之前,又有新的读者与写者到达,仍然是写者排在前面)二、算法的基本思想设计思想分别用三个队列来存放输入的数据的PRO1队列和就绪的读者进程写者进程的队列PRO2和和正在运行的读者写者队列PRO3。只有当互斥信号量WMUTEX=1表示无资源占用CPU,写者进入PRO3进行写。当互斥信号量若WMUTEX=0表示有资源占用CPU,若READCOUNT0说明有读者再读,由于读写互斥,写者不操作,等待。若当前读者数READCOUNT=0时,有写者,因为写写互斥,写者不进入,等待。涉及到的数据结构structThreadInfo{intnSerialNo;//线程序号charcType;//线程类别(判断是读者还是写者线程)intdDelayTime;//线程开始时间intdOpeTime;//线程操作时间intruntime;//线程运行时间structThreadInfo*next;};基本功能模块读者写者问题写优先查看读者写者信息退出4主函数模块1)函数原形:voidmain();2)功能:初始化链表,调用menu()函数显示主界面就绪模块1)函数原形:voidready(inti)2)功能:把pro1中就绪的读者写者信息移到队列pro2尾部3)变量及类型:ThreadInfo*p,*q,*j,*k;:定义指针变量,使队列变量intflag=0;标记,为0时,未开辟空间,为1时,,开辟空间,需释放显示模块1)函数原形:voidprint1()voidprint2()2)功能:print1()函数,显示文件中读者写者的信息,print2()函数显示写优先的读者写者进程运行情况。排序模块函数原形:voidsort()2)功能:给就绪队列pro2排序,写者排在前,读者往后排。3)变量及类型:ThreadInfo*p,*q,*j,*k;j是写者链表,p是其移动指针,k是读者链表,q是其移动指针添加模块1)函数原形:voidadd1(inti)2)功能:给pro1增加一个读者或写者信息3)变量及类型:手动输入文件读取5三、主要功能模块流程6开始显示主界面,进行选择if(ch=2)If(ch=1)If(ch=0)查看文件和信息手动输入从文件读取提示保存退出结束显示“写优先”的读者写者运行情况是否增加读者写者输入要增加的信息显示增加了一个读者写者的“写优先”读写运行情况NY7四、系统测试1.选择1,运行界面如下:选择1,运行界面如下89选择2,运行界面如下10运行过程中增加一个读者或写者,界面如下2.选择2,运行界面如下:11五.结论感想:在本次实验中程序曾多次编译、运行出错,多亏了周影老师的指导才将错误找出并改正,通过本次实验,我认识到实践和动手的重要性。缺陷:运行过程中没有用可视化界面动态显示,不能查看阅览室中读者/写者数目、等待队列、写者等待队列、读写时间、等待时间,但是可以查看阅览师中读者或写者和等待队列中的读者或写者。六.源程序及系统文件使用说明程序清单#includewindows.h#includestdlib.h#includefstream.h#includeio.h#includestring.h#includestdio.hvoidprint2();structThreadInfo{intnSerialNo;//线程序号charcType;//线程类别(判断是读者还是写者线程)intdDelayTime;//线程开始时间intdOpeTime;//线程操作时间intruntime;//线程运行时间structThreadInfo*next;};structThreadInfo*h=NULL;intWmutex=1;//互斥读写的信号量,1没有人占用cpu,能进入intreadcount=0;//当前读者人数#definethreadsizeof(structThreadInfo)intm=0;ThreadInfo*pro1=NULL,*pro2=NULL,*pro3=NULL;//定义三个队列,pro1为输入数据队列,pro2为就绪队列,pro3为运行队列voidsave()//把h中内容保存到文件中{structThreadInfo*p=NULL;FILE*fp;p=h;if((fp=fopen(thread.txt,wb))==NULL)12{printf(创建文件失败!\n);fflush(stdin);getchar();return;}while(p!=NULL){if(fwrite(p,thread,1,fp)==0){printf(向文件输入数据失败\n);break;}elsep=p-next;}fprintf(fp,%d,m);fclose(fp);}intread(){FILE*fp;//定义文件指针structThreadInfo*p=NULL,*q;h=(structThreadInfo*)malloc(thread);h-next=NULL;p=h;if((fp=fopen(thread.txt,rb))==NULL)//打开文件,并判断是否出错{cout出错,请检查文件是否存在,按任意键后回车返回住菜单\n\n\n;//打印出错提示fflush(stdin);getchar();return0;}while(!feof(fp)){q=(structThreadInfo*)malloc(thread);q-next=NULL;fread(q,thread,1,fp);fscanf(fp,%d,&m);p-next=q;p=p-next;}p=h-next;13h-next=NULL;free(h);h=p;fclose(fp);//关闭文件return1;}voidprint1(){structThreadInfo*p=NULL;cout输出队列信息:\n\n;if(read()==0)return;//调用读取文件函数,并判断是否文件存在。p=h;cout********************************************************\n\n;cout线程序号线程类型读入内存时间写时间\n;while(p!=NULL){coutp-nSerialNo\t\tp-cType\t\tp-dDelayTime\tp-dOpeTimeendl;//打印信息p=p-next;}}voidinput(){structThreadInfo*p=NULL;inti,num;inty;p=h;cout\n请输入要输入的读者和写者个数:;fflush(stdin);//清除文件缓冲区cinnum;system(CLS);/*清屏*/cout输入信息:\n;cout-----------------------------------------------\n;for(i=0;inum;i++){cout线程序号:;fflush(stdin);cinp-nSerialNo;cout输入线程类别:;fflush(stdin);14cinp-cType;cout输入读入内存时间:;fflush(stdin);cinp-dDelayTime;cout输入读写时间:;fflush(stdin);cinp-dOpeTime;p-runtime=0;p-next=(structThreadInfo*)malloc(thread);p=p-next;p-next=NULL;m++;}p=h;//把输入内容存入链表h中,再把h赋给pro1while(p-next-next!=NULL)p=p-next;p-next=NULL;pro1=h;cout信息输入完毕,是否存盘:存盘按0,不存盘按其他任意键后回车;fflush(stdin);ciny;if(y==0){save();//将结构体信息存盘}}voidadd1(inti)//给pro1增加一个读者或写者信息{ThreadInfo*p,*q;inta;p=pro1;q=(ThreadInfo*)malloc(thread);printf(线程序号:);scanf(%d,&q-nSerialNo);printf(\n);printf(输入线程类别:);fflush(stdin);scanf(%c,&q-cType);printf(\n);printf(输入读写时间:);scanf(%d,&a);q-dDelayTime=a+i;printf(\n);printf(输入读写时间:);scanf(%d,&q-dOpeTime);15q-runtime=0;q-next=NULL;FILE*fp;fp=fopen(thread.txt,ab);fwrite(q,thread,1,fp);fprintf(fp,%d,m);fclose(fp);if(pro1!=NULL){while(p-next!=NULL)p=p-next;p-next=q;}elsepro1=q;}intwait(int&a)//申请{a--;if(a0){return0;}return1;}voidsignal(int&a)//释放{a++;}voidready(inti)//就绪队列pro2,从pro1移到pro2尾部{ThreadInfo*p,*q,*j,*k;p=pro1;q=pro2;intflag=0;//t为标记,为0时,未开辟空间if(pro2==NULL){q=pro2=(ThreadInfo*)malloc(thread);q-next=NULL;//q始终指向pro2尾部flag=1;//开辟一空间,设1,需释放}else{16while(q-next!=NULL){q=q-next;}}j=(ThreadInfo*)malloc(thread);j-next=pro1;while(pro1-dDelayTime==i)//i为时间片{q-next=pro1;pro1=pro1-next;q=q-next;q-next=NULL;j-next=pro1;if(pro1==NULL)break;}p=pro1;while(p!=NULL){if(p-dDelayTime==i){k=j;while(k-next!=p){k=k-next;}k-next=p-next;q-next=p;q=q-next;p=p-next;q-n
本文标题:读者写者问题
链接地址:https://www.777doc.com/doc-3668910 .html