收藏 分销(赏)

进程同步模拟设计——读者和写者问题.doc

上传人:天**** 文档编号:2076213 上传时间:2024-05-15 格式:DOC 页数:18 大小:197.54KB 下载积分:8 金币
下载 相关 举报
进程同步模拟设计——读者和写者问题.doc_第1页
第1页 / 共18页
进程同步模拟设计——读者和写者问题.doc_第2页
第2页 / 共18页


点击查看更多>>
资源描述
______________________________________________________________________________________________________________ 学 号: 课 程 设 计 题 目 进程同步模拟设计——读者和写者问题 学 院 计算机科学与技术学院 专 业 、 班 级 、 姓 名 、 指导教师 吴利军 2013 年 01 月 17 日 课程设计任务书 学生姓名: 指导教师: 吴利军 工作单位: 计算机科学与技术学院 题 目: 进程同步模拟设计——读者和写者问题 初始条件: 1.预备内容:阅读操作系统的进程管理章节内容,对进程的同步和互斥,以及信号量机制度有深入的理解。 2.实践准备:掌握一种计算机高级语言的使用。 要求完成的主要任务: (包括课程设计工作量及其技术要求,以及说明书撰写等具体要求) 1.模拟用信号量机制实现读者和写者问题。 2.设计报告内容应说明: ⑴ 需求分析; ⑵ 功能设计(数据结构及模块说明); ⑶ 开发平台及源程序的主要部分; ⑷ 测试用例,运行结果与运行情况分析; ⑸ 自我评价与总结: i)你认为你完成的设计哪些地方做得比较好或比较出色; ii)什么地方做得不太好,以后如何改正; iii)从本设计得到的收获(在编写,调试,执行过程中的经验和教训); iv)完成本题是否有其他方法(如果有,简要说明该方法); 时间安排: 设计安排一周:周1、周2:完成程序分析及设计。 周2、周3:完成程序调试及测试。 周4、周5:验收、撰写课程设计报告。 (注意事项:严禁抄袭,一旦发现,一律按0分记) 指导教师签名: 年 月 日 系主任(或责任教师)签名: 年 月 日 1 需求分析 所谓读者写者问题,是指保证一个 writer 进程必须与其他进程互斥地访问共享资源的同步问题.读者写者问题可以这样的描述,有一群写者和一群读者, 写者在写同一本书,读者也在读这本书,多个读者可以同时读这本书,但是只能有一个写者在写书,并且读者优先,也就是说,读者和写者同时提出请求时,读者优先.当读者提出请求时需要有一个互斥操作, 另外需要有一个信号量 mutex来当前是否可操作.信号量机制是支持多道程序的并发操作系统设计中解决资源共享时进程间的同步与互斥的重要机制,而读者写者问题则是这一机制的一个经典范例. 与记录型信号量解决读者—写者问题不同,信号量机制它增加了一个限制,即最多允许n个读者同时读.为此引入了一个信号量Rcount,并赋予初值为 0,通过执行Rcount++操作,来控制读者的数目,每当有一个读者进入时,就要执行Rcount++操作,使 Rcount 的值加1.读者离开时Rcount--;当且仅当Rcount==0时,V(Wmutex),才能进行写操作。对利用信号量来解决读者—写者问题的描述如下: Wmutex表示读写的互斥信号量,初值:Wmutex =1; 公共变量Rcount表示“正在读”的进程数,初值:Rcount =0; Rmutex:表示对Rcount的互斥操作,初值:Rmutex=1。 main() { int Wmutex=1; int Rmutex=1; int Rcount=0; cobegin read 1(); read 2(); read 3(); ...... write 1(); write2 (); write3 (); ...... coend } readn() { P(Rmutex); Rcount++; if (Rcount==1) P (Wmutex); V(Rmutex); 读 P(Rmutex); Rcount--; if (Rcount==0)V(Wmutex); V(Rmutex); } writen() { P(Wmutex); 写 V(Wmutex); } 2功能设计 2.1 设计目的 l. 用信号量来实现读者写者问题. 2 .理解和运用信号量,PV 原语,进程间的同步互斥关系等基本知识. 2.2设计内容 读者写者问题的定义如下:有一个许多进程共享的数据区,这个数据区可以 是一个文件或者主存的一块空间;有一些只读取这个数据区的进程(Reader)和 一些只往数据区写数据的进程(Writer),此外还需要满足以下条件: (1) 任意多个读进程可以同时读这个文件; (2)一次只有一个写进程可以往文件中写; (3)如果一个写进程正在进行操作,禁止任何读进程度文件. 我们需要分两种情况实现该问题: 读优先:要求指一个读者试图进行读操作时,如果这时正有其他读者在进行操作,他可直接开始读操作,而不需要等待. 写优先:一个读者试图进行读操作时,如果有其他写者在等待进行写操作或 正在进行写操作,他要等待该写者完成写操作后才开始读操作. 2.3设计分析 在 Windows xp 环境下,创建一个包含 n 个线程的控制台进程.用这 n 个线程来表示 n 个读者或写者. 每个线程按相应测试数据文件的要求, 进行读写操作. 请用信号量机制分别实现读者优先和写者优先的读者-写者问题. 读者-写者问题的读写操作限制: 读者-写者的读写限制(包括读者优先和写者优先) 1)写-写互斥,即不能有两个写者同时进行写操作 2)读-写互斥,即不能同时有一个读者在读,同时却有一个写者在写 3)读读允许,即可以有 2 个以上的读者同时读 将所有的读者和所有的写者分别放进两个等待队列中, 当读允许时就让读者 队列释放一个或多个读者,当写允许时,释放第一个写者操作.读者写者问题的 定义如下:有一个许多进程共享的数据区,这个数据区可以是一个文件或者主存 的一块空间;有一些只读取这个数据区的进程(Reader)和一些只往数据区写数 据的进程(Writer),此外还需要满足以下条件:1)任意多个读进程可以同时读这 个文件;2) 一次只有一个写进程可以往文件中写;3)如果一个写进程正在进行操作,禁止任何读进程度文件. 3开发平台及源程序主要部分 3.1开发平台 Windows xp 系统下,VC++6.0开发 3.2源程序主要部分 结构体_Person如下 typedef struct _Person { HANDLE m_hThread;//定义处理线程的句柄 int m_nType;//进程类型(读写) int m_nStartTime;//开始时间 int m_nWorkTime;//运行时间 int m_nID;//进程号 }Person; main()函数(主线程) 创建信号灯,当前可用的资源数为 1,最大为 100 : g_hReadSemaphore = CreateSemaphore(NULL,1,100,NULL) g_hWriteSemaphore = CreateSemaphore(NULL,1,100,NULL) 调用CreatePersonList()函数,设置线程同步间隔为1000ms,计算时间片。 CreatePersonList(int *pPersonLists)函数 根据*pPersonLists队列创建读者/写者。 CreateReader(int StartTime,int WorkTime,int ID)函数 创建与读者有关的线程,并初始化g_Persons [g_NumPerson] CreateWriter(int StartTime,int WorkTime,int ID)函数 创建与写者有关的线程,并初始化g_Persons [g_NumPerson] DWORD WINAPI ReaderProc(LPVOID lpParam)和DWORD WINAPI WriterProc(LPVOID lpParam) 分别与读者和写者对应的辅助线程函数。 3.3程序流程图 CreatePersonList() CreateWriter() CreateReader() WriterProc() ReaderProc() 退出 W R Main() 4 测试用例和运行结果 4.1测试用例 int g_PersonLists[] = { 1, W,1,3, 2, W,3,1, 3, R,10,2, 4, W,6,3, 5, R,7,5, 6, R,9,1, END, }; 4.2运行结果 4.3运行结果分析 进程1是写操作,在时间片1进入队列,运行时间3,在它进入时没有进程占用资源,立即占用资源,直到释放资源。在它占用资源时等待的进程有:2 进程2是写操作,在时间片3进入队列,运行时间1,由于进程1在占用资源,所以等待进程1释放资源。在它占用资源时没有等待的进程 进程3是读操作,在时间片10进入队列,运行时间2,此时读者5在占用资源,但由于可以多个读者同时阅读,所以读者3也可以阅读 进程4是写操作,在时间片6进入队列,运行时间3,此时没有进程占用资源,它可以立即占用资源,直到结束并释放资源。在它占用资源时等待的进程有:5,6 进程5是读操作,在时间片7进入队列,运行时间5,由于此时进程4在占用资源,所以等待进程4释放资源。 进程6是读操作,在时间片9进入队列,运行时间1,由于此时进程4在占用资源,所以等待进程4释放资源。 由于可以多个读者同时阅读,所以读者3,5,6在时间片10同时阅读。 5自我评价与总结 通过这次操作系统的课程设计,我研究了读者与写者问题,进一步深入了解了同步与互斥机制。比如什么是同步,什么是互斥,什么是信号量等等。 课程设计和平时的实验课比较起来有很大的差距,实验课只是将这一章的一部分内容练习操作一遍,而课程设计需要的是他们综合起来的东西,这要更难一些。 总体来说我认为操作系统这门学科在计算机科学当是中非常重要的。他将我们学过的编程语言联系起来,可以说是第一次利用C语言利用windows的API与系统进行“沟通”。 总而言之,这次操作系统的课程设计收获颇丰,复习了许多东西,也从新学会了许多东西。我想这也许就是课程设计的最终目的吧。 6源程序 #include <windows.h> #include <ctype.h> #include <stdio.h> #include <string.h> #include <stdlib.h> #include <malloc.h> #define MAX_PERSON 100 #define READER 0 //读者 #define WRITER 1 //写者 #define END -1 #define R READER #define W WRITER typedef struct _Person { HANDLE m_hThread;//定义处理线程的句柄 int m_nType;//进程类型(读写) int m_nStartTime;//开始时间 int m_nWorkTime;//运行时间 int m_nID;//进程号 }Person; Person g_Persons[MAX_PERSON]; int g_NumPerson = 0; long g_CurrentTime= 0;//基本时间片数 int g_PersonLists[] = { 1, W,1,3, 2, W,3,1, 3, R,10,2, 4, W,6,3, 5, R,7,5, 6, R,9,1, END, }; //队列 int g_NumOfReading = 0; int g_NumOfWriteRequest = 0;//申请写进程的个数 HANDLE g_hReadSemaphore;//读者信号 HANDLE g_hWriteSemaphore;//写者信号 bool finished = false; //所有的读完成 bool wfinished = false; //所有的写完成 void CreatePersonList(int *pPersonList); bool CreateReader(int StartTime,int WorkTime,int ID); bool CreateWriter(int StartTime,int WorkTime,int ID); DWORD WINAPI ReaderProc(LPVOID lpParam); DWORD WINAPI WriterProc(LPVOID lpParam); int main() { g_hReadSemaphore = CreateSemaphore(NULL,1,100,NULL); //创建信号灯,当前可用的资源数为 1,最大为 100 g_hWriteSemaphore = CreateSemaphore(NULL,1,100,NULL); //创建信号灯,当前 可用的资源数为 1,最大为 100 printf("开始...\n"); CreatePersonList(g_PersonLists); //创建读者与写者 g_CurrentTime = 0; while(true) { g_CurrentTime++; Sleep(500); printf("时间片 = :%d\n",g_CurrentTime); if(finished) return 0; } return 0; } void CreatePersonList(int *pPersonLists) { int i=0; int *pList = pPersonLists; bool Ret; while(pList[0] != END) { switch(pList[1]) { case R: Ret = CreateReader(pList[2],pList[3],pList[0]); break; case W: Ret = CreateWriter(pList[2],pList[3],pList[0]); break; } if(!Ret) printf("创建 %d 失败\n",pList[0]); pList += 4; // move to next person list } } DWORD WINAPI ReaderProc(LPVOID lpParam)//读过程 { Person *pPerson = (Person*)lpParam; while(g_CurrentTime != pPerson->m_nStartTime) // 等待开始 {} printf(" 读者 %d 正在申请资源 ...\n",pPerson->m_nID); WaitForSingleObject(g_hReadSemaphore,INFINITE); // 等待对象被触发信号 if(g_NumOfReading ==0) { WaitForSingleObject(g_hWriteSemaphore,INFINITE); } g_NumOfReading++; ReleaseSemaphore(g_hReadSemaphore,1,NULL); pPerson->m_nStartTime = g_CurrentTime; printf(" 读者 %d 正在阅读...\n",pPerson->m_nID); while(g_CurrentTime <= pPerson->m_nStartTime + pPerson->m_nWorkTime) {} printf(" 读者 %d 正在退出...\n",pPerson->m_nID); WaitForSingleObject(g_hReadSemaphore,INFINITE); g_NumOfReading--; if(g_NumOfReading == 0) { ReleaseSemaphore(g_hWriteSemaphore,1,NULL);//此时没有读者,可以写 } ReleaseSemaphore(g_hReadSemaphore,1,NULL); if(pPerson->m_nID == 4) finished = true; //所有的读写完成 ExitThread(0); return 0; } DWORD WINAPI WriterProc(LPVOID lpParam) { Person *pPerson = (Person*)lpParam; while(g_CurrentTime != pPerson->m_nStartTime) // 等待开始 {} printf(" 写者 %d 正在申请资源...\n",pPerson->m_nID); WaitForSingleObject(g_hWriteSemaphore,INFINITE); // 等待对象被触发信号 pPerson->m_nStartTime = g_CurrentTime; printf(" 写者 %d 正在写入...\n",pPerson->m_nID); while(g_CurrentTime <= pPerson->m_nStartTime + pPerson->m_nWorkTime) {} printf(" 写者 %d 正在退出...\n",pPerson->m_nID); g_NumOfWriteRequest--; ReleaseSemaphore(g_hWriteSemaphore,1,NULL); if(pPerson->m_nID == 4) finished = true;//所有的读写完成 ExitThread(0); return 0; } bool CreateReader(int StartTime,int WorkTime,int ID) { if(g_NumPerson >= MAX_PERSON) return false; Person *pPerson = &g_Persons[g_NumPerson]; pPerson->m_nID = ID; pPerson->m_nStartTime = StartTime; pPerson->m_nWorkTime = WorkTime; pPerson->m_nType = READER; g_NumPerson++; pPerson->m_hThread= CreateThread(NULL,0,ReaderProc,(LPVOID)pPerson,0,NULL); // 创建新线程 if(pPerson->m_hThread == NULL) return false; return true; } bool CreateWriter(int StartTime,int WorkTime,int ID) { if(g_NumPerson >= MAX_PERSON) return false; Person *pPerson = &g_Persons[g_NumPerson]; pPerson->m_nID = ID; pPerson->m_nStartTime = StartTime; pPerson->m_nWorkTime = WorkTime; pPerson->m_nType= WRITER; g_NumPerson++; pPerson->m_hThread= CreateThread(NULL,0,WriterProc,(LPVOID)pPerson,0,NULL); //创建新线程 if(pPerson->m_hThread == NULL) return false; return true; } 本科生课程设计成绩评定表 序号 评分项目 满分 实得分 1 学习态度认真、遵守纪律 10 2 设计分析合理性 10 3 设计方案正确性、可行性、创造性 20 4 设计结果正确性 40 5 设计报告的规范性 10 6 设计验收 10 总得分/等级 评语: 注:最终成绩以五级分制记。优(90-100分)、良(80-89分)、中(70-79分)、 及格(60-69分)、60分以下为不及格                       指导教师签名:                   2013 年 1月 17日 精品资料 Welcome To Download !!! 欢迎您的下载,资料仅供参考! 精品资料
展开阅读全文

开通  VIP会员、SVIP会员  优惠大
下载10份以上建议开通VIP会员
下载20份以上建议开通SVIP会员


开通VIP      成为共赢上传

当前位置:首页 > 考试专区 > 中考

移动网页_全站_页脚广告1

关于我们      便捷服务       自信AI       AI导航        抽奖活动

©2010-2025 宁波自信网络信息技术有限公司  版权所有

客服电话:4009-655-100  投诉/维权电话:18658249818

gongan.png浙公网安备33021202000488号   

icp.png浙ICP备2021020529号-1  |  浙B2-20240490  

关注我们 :微信公众号    抖音    微博    LOFTER 

客服