模拟电梯调度算法,实现对磁盘的驱动调度。

合集下载

磁盘调度算法的模拟实现及对比

磁盘调度算法的模拟实现及对比

磁盘调度算法的模拟实现及对比磁盘调度算法是操作系统中的一个重要组成部分,用于优化磁盘读写操作的效率,提高系统的响应速度和运行效率。

常见的磁盘调度算法包括先来先服务(FCFS)算法、最短寻道时间优先(SSTF)算法、电梯(Elevator)算法等。

在进行磁盘调度算法的比较和模拟之前,我们首先需要了解磁盘读写操作的基本原理。

磁盘是由许多磁道和扇区组成的,当操作系统需要对磁盘进行读写操作时,读写头需要按照特定的路径移动到目标扇区,这个过程称为寻道。

而磁头在寻道的过程中所花费的时间称为寻道时间。

不同的磁盘调度算法的主要目标就是使得寻道时间尽可能地短,从而提高磁盘的读写操作效率。

首先,我们来实现一个先来先服务(FCFS)算法的模拟。

FCFS算法是最简单的磁盘调度算法,它按照磁盘请求的先后顺序进行处理。

具体实现如下:```pythondef fcfs(disk_queue, start):head_movement = 0curr_pos = startfor request in disk_queue:head_movement += abs(request - curr_pos)curr_pos = requestreturn head_movement```上述代码中,`disk_queue`表示磁盘请求队列,`start`表示起始磁道号。

算法首先将磁头移动到起始磁道号`start`,然后按照磁盘请求的先后顺序对队列中的请求进行处理,计算磁头的移动距离。

最后返回磁头的总移动距离。

接下来,我们实现一个最短寻道时间优先(SSTF)算法的模拟。

SSTF 算法会选择离当前磁道最近的请求进行处理,从而减少磁头的寻道时间。

具体实现如下:```pythondef sstf(disk_queue, start):head_movement = 0curr_pos = startwhile disk_queue:min_distance = float('inf')min_index = -1for i, request in enumerate(disk_queue):distance = abs(request - curr_pos)if distance < min_distance:min_distance = distancemin_index = ihead_movement += min_distancecurr_pos = disk_queue.pop(min_index)return head_movement```上述代码中,算法首先将磁头移动到起始磁道号`start`,然后不断选择离当前磁道最近的请求处理,直到所有请求处理完毕。

磁盘调度操作系统实验报告

磁盘调度操作系统实验报告

磁盘调度操作系统实验报告一、实验目的:本次实验主要目的是通过模拟实现磁盘调度算法,加深对操作系统磁盘调度原理的理解,并学会使用操作系统磁盘调度算法解决实际问题。

二、实验内容:1.磁盘调度算法原理分析:磁盘调度算法是操作系统中的重要组成部分,它的任务是合理安排磁盘上数据的存取顺序,以提高磁盘的效率。

常见的磁盘调度算法有先来先服务(FCFS)、最短寻道时间优先(SSTF)、电梯算法(SCAN)等。

2.模拟实现磁盘调度算法:本实验选择最短寻道时间优先算法(SSTF)作为示例进行模拟实现。

SSTF算法的原理是优先选择离当前磁头位置最近的磁道进行访问,以减少磁头移动时间。

实验步骤:1.根据实际情况,创建一个磁道队列,记录需要访问的磁道序号。

2.初始化磁盘的起始位置和访问队列。

3.对访问队列进行排序,按照磁头当前位置到磁道的距离从小到大排列。

4.根据排序后的队列顺序,依次访问磁道,并记录磁头移动的距离。

5.计算平均寻道长度。

三、实验结果分析:通过模拟实现SSTF磁盘调度算法,我们获得了磁头对每个磁道的访问顺序和总共的磁头移动距离。

根据实验结果,我们可以发现SSTF算法相对于其他算法具有一定的优势。

在实际应用中,根据不同的实际情况,可以选择合适的磁盘调度算法以优化磁盘的访问效率。

四、实验总结:通过本次实验,我们对磁盘调度算法的原理和实现有了更深入的了解。

磁盘调度算法作为操作系统中一个重要的模块,对提高磁盘的读写效率起着重要的作用。

在实际应用中,我们需要根据具体问题选择合适的磁盘调度算法,以达到最优的访问效果。

磁盘驱动调度算法的模拟

磁盘驱动调度算法的模拟

实验四磁盘驱动调度算法的模拟一.实验内容:熟悉磁盘的结构以及磁盘的驱动调度算法的模拟,编程实现简单常用的磁盘驱动调度算法先来先服务(FIFO)、电梯调度算法、最短寻找时间优先算法、扫描(双向扫描)算法、单向扫描(循环扫描)算法等。

编程只需实现两个算法。

题目可以选取教材或习题中的相关编程实例。

编程语言建议采用c/c++或Java。

模拟程序鼓励采用随机数技术、动态空间分配技术,有条件的最好能用图形界面展现甚至用动画模拟。

实验性质:验证型。

二.实验目的和要求1)掌握使用一门语言进行磁盘驱动调度算法的模拟;2)编写程序将磁盘驱动调度算法的过程和结果能以较简明直观的方式展现出来。

三.实验原理、方法和步骤1. 实验原理磁盘驱动调度对磁盘的效率有重要影响。

磁盘驱动调度算法的好坏直接影响辅助存储器的效率,从而影响计算机系统的整体效率。

常用的磁盘驱动调度算法有:最简单的磁盘驱动调度算法是先入先出(F IFO)法。

这种算法的实质是,总是严格按时间顺序对磁盘请求予以处理。

算法实现简单、易于理解并且相对公平,不会发生进程饿死现象。

但该算法可能会移动的柱面数较多并且会经常更换移动方向,效率有待提高。

最短寻找时间优先算法:总是优先处理最靠近的请求。

该算法移动的柱面距离较小,但可能会经常改变移动方向,并且可能会发生进程饥饿现象。

电梯调度:总是将一个方向上的请求全部处理完后,才改变方向继续处理其他请求。

扫描(双向扫描):总是从最外向最里进行扫描,然后在从最里向最外扫描。

该算法与电梯调度算法的区别是电梯调度在没有最外或最里的请求时不会移动到最外或最里柱面,二扫描算法总是移到最外、最里柱面。

两端的请求有优先服被务的迹象。

循环扫描(单向扫描):从最外向最里进行柱面请求处理,到最里柱面后,直接跳到最外柱面然后继续向里进行处理。

该算法与扫描算法的区别是,回来过程不处理请求,基于这样的事实,因为里端刚被处理。

2. 实验方法1)使用流程图描述演示程序的设计思想;2)选取c/c++、Java等计算机语言,编程调试,最终给出运行正确的程序。

操作系统课程设计-模拟电梯调度算法 实现对磁盘的驱动调度

操作系统课程设计-模拟电梯调度算法 实现对磁盘的驱动调度

衡阳师范学院操作系统课程设计报告设计题目:驱动调度系别:计算机科学系专业:计算机科学与技术(师范)班级:1001班姓名:XXX学号:XXX指导教师:XXX2012年11月26日目录一、程序设计内容原理及目的·······························1、设计内容················································`2、设计原理·················································3、设计目的·················································二、程序设计过程·········································1、驱动调度中的数据结构设计·································2、程序算法设计··············································三、用户手册··············································1、运行坏境··················································2、执行文件··················································四、程序实现及运行结果····································1、源代码····················································2、代码······················································3、运行结果·················································五、心得总结···············································六、参考文献···············································二、程序设计内容原理及目的1、设计内容模拟电梯调度算法,实现对磁盘的驱动调度。

驱动调度算法

驱动调度算法

驱动调度算法一、实验目的磁盘是一种高速、大容量、旋转型、可直接存取的存储设备。

他作为计算机系统的辅助存储器,担负着输入输出任务,在多道程序设计系统中,往往同时会有这若干个要求访问磁盘的输入输出请求等待处理。

系统课采用一种策略,尽可能按最佳次序执行要求访问磁盘的诸多输入输出请求。

这就叫驱动调度,使用的算法叫驱动算法。

二,实验内容模拟电梯调度算法,实现对磁盘的驱动调度。

三,源程序#include<stdio.h>#include<stdlib.h>#include<iostream.h>#include<math.h>#define maxsize 1000int decide(char str[]) //判断输入数据是否有效{int i=0;while(str[i]!='\0'){if(str[i]<'0'||str[i]>'9'){return 0;break;}i++;}return i;}int trans(char str[],int a) //将字符串转换成数字{int i;int sum=0;for(i=0;i<a;i++){sum=sum+(int)((str[i]-'0')*pow(10,a-i-1));}return sum;}int *bubble(int cidao[],int m){int i,j;int temp;for(i=0;i<m;i++) //使用冒泡法按从小到大顺序排列for(j=i+1;j<m;j++){if(cidao[i]>cidao[j]){temp=cidao[i];cidao[i]=cidao[j];cidao[j]=temp;}}cout<<"排序后的磁盘序列为:";for( i=0;i<m;i++) //输出排序结果{cout<<cidao[i]<<" ";}cout<<endl;return cidao;}void FCFS(int cidao[],int m) //先来先服务调度算法{int now; //当前磁道号int sum=0; //总寻道长度int j,i;int a;char str[100];float ave; //平均寻道长度cout<<"磁盘请求序列为:";for( i=0;i<m;i++) //按先来先服务的策略输出磁盘请求序列{cout<<cidao[i]<<" ";}cout<<endl;cout<<"请输入当前的磁道号:";B: cin>>str; //对输入数据进行有效性判断a=decide(str);if(a==0){cout<<"输入数据的类型错误,请重新输入!"<<endl;goto B;}elsenow=trans(str,a); //输入当前磁道号sum+=abs(cidao[0]-now);cout<<"磁盘扫描序列为:";for( i=0;i<m;i++) //输出磁盘扫描序列{cout<<cidao[i]<<" ";}for(i=0,j=1;j<m;i++,j++) //求平均寻道长度{sum+=abs(cidao[j]-cidao[i]);ave=(float)(sum)/(float)(m);}cout<<endl;cout<<"平均寻道长度:"<<ave<<endl;}void SSTF(int cidao[],int m) //最短寻道时间优先调度算法{int k=1;int now,l,r;int i,j,sum=0;int a;char str[100];float ave;cidao=bubble(cidao,m); //调用冒泡排序算法排序cout<<"请输入当前的磁道号:";C: cin>>str; //对输入数据进行有效性判断a=decide(str);if(a==0){cout<<"输入数据的类型错误,请重新输入!"<<endl;goto C;}elsenow=trans(str,a); //输入当前磁道号if(cidao[m-1]<=now) //若当前磁道号大于请求序列中最大者,则直接由外向内依次给予各请求服务{cout<<"磁盘扫描序列为:";for(i=m-1;i>=0;i--)cout<<cidao[i]<<" ";sum=now-cidao[0];}if(cidao[0]>=now) //若当前磁道号小于请求序列中最小者,则直接由内向外依次给予各请求服务{cout<<"磁盘扫描序列为:";for(i=0;i<m;i++)cout<<cidao[i]<<" ";sum=cidao[m-1]-now;}if(now>cidao[0]&&now<cidao[m-1]) //若当前磁道号大于请求序列中最小者且小于最大者{cout<<"磁盘扫描序列为:";while(cidao[k]<now) //确定当前磁道在已排的序列中的位置,后面的算法都用到了,可以直接复制后少量修改,节省时间。

操作系统驱动调度

操作系统驱动调度

操作系统实习报告姓名学号日期实验室指导教师设备编号实习题目实习九驱动调度一、实习内容模拟电梯调度算法,实现对磁盘的驱动调度。

二、实习目的磁盘是一种高速、大容量、旋转型、可直接存取的存储设备。

它作为计算机系统的辅助存储器,担负着繁重的输入输出任务、在多道程序设计系统中,往往同时会有若干个要求访问磁盘的输入输出请求等待处理。

系统可采用一种策略,尽可能按最佳次序执行要求访问磁盘的诸输入输出请求。

这就叫驱动调度,使用的算法称为驱动调度算法。

驱动调度能降低为若干个输入输出请求服务所需的总时间,从而提高系统效率。

本实验要求学生模拟设计一个驱动调度程序,观察驱动调度程序的动态运行过程。

通过实验使学生理解和掌握驱动调度的职能。

三、实习过程1.数据结构设计#define M 20typedef struct PCB{charproc[M];//进程名int cylinder_num;//柱面号int track_num;//磁道号int phy_num;//物理记录号struct PCB *next;}PCB;2.算法设计(1) 主函数框图如图1.1)主函数要求用户选择大于0.5 <电梯调度>小于0.5 <接受请求>2)进入模拟程序调用函数对输入值进行判定。

3)输入值大于0.5 初始化数组。

调用lift( )函数。

调用电梯调度算法。

调用输出函数output。

4)输入值小于0.5 调用接受请求函数。

接受进程输入请求,写入链表。

调用输出函数output。

5)要求用户选择是否继续Y.继续N.退出(2) 电梯调度算法lift() 如图3.1) 查I/O请求表,若等待进程表中有进程,则继续。

否则返回。

2) 若有与当前运行的进程的柱面号相同的进程访问,则选择能使旋转距离最短的访问者,并登记当前位置。

否则继续判断当前移臂方向。

3) 若当前移臂方向向里,则判断是否有比当前柱面号大的访问请求;否则判断是否有比当前柱面号小的访问请求。

实验二 模拟实现磁盘调度算法

实验二  模拟实现磁盘调度算法

实验二模拟实现磁盘调度算法姓名:班级:软件工程二班学号:日期:2020年12月13日实验目的:a、观察、体会操作系统的磁盘调度方法,并通过一个简单的磁盘调度模拟程序的实现,加深对磁盘调度的理解。

b、提高实际动手编程能力,为日后从事软件开发工作打下坚实基础。

实验内容:a、模拟实现磁盘调度算法:FCFS,最短寻道优先,电梯算法(参照给定的算法实现最短寻道优先算法,电梯算法(磁头向外))。

b、磁道请求服务顺序由用户输入(可通过从指定的文本文件(TXT文件)中取出)。

基本思想、原理和算法描述:(1)电梯算法磁头初始向外:思想和原理:用户输入一个初始磁道号,规定向外和向内,向外即先逐渐减小,当向外遍历完后,就掉头向里,向里则是逐渐增大。

设置一个变量了定义进程是否已经执行,每执行完一个就给它赋值,下次就不遍历。

算法描述:首先调用重置访问标志、磁头当前位置、总移动磁道数的函数,然后进入循环,在循环刚开始时候,定义一个非常大的容器用来存储移动磁道数。

比较移动磁道数的大小,把小的那个磁道的下标给iNEXT,并把移动磁道数改为当前磁道的磁道移动数,用于下一次比较。

然后累加总移动磁道数,移动磁头当前位置为当前访问磁道号,并设置磁道是否已经访问标志为1:已访问。

(2)最短寻道优先调度算法:思想和原理:要求访问的磁道与当前磁头所在的磁道距离最近,即要求移动的磁道数最小的后一个磁道先执行。

主要是比较下一个磁道与当前磁道的差,取差最小的那个磁道,后面以此类推。

算法描述:源程序和电梯算法相似,本算法只比较移动磁道数的大小。

循环比较,直到所有的磁道都遍历完。

源程序:(1)电梯算法磁头初始向外:case 2://磁头初始向外Reset();//重置访问标志、磁头当前位置、总移动磁道数cout<<endl<<"---------------------------------------------"<<endl;cout<<"电梯调度算法——磁头初始向外的调度结果: "<<endl<<endl;cout<<"初始磁道号: "<<iStart<<endl;cout<<"序号下一磁道号移动的磁道数"<<endl;for(i=0;i<iReqNum;i++){iMinMove=9999;iNext=-1;for(j=0;j<iReqNum;j++)//寻找当前方向上寻道距离最短的未访问磁道号在数组队列queue中的下标{if((queue[j].iBeVisited==0)&&(queue[j].iGo<=iNow)){if(abs(queue[j].iGo-iNow)<iMinMove){iNext=j;iMinMove=abs(queue[j].iGo-iNow);} //if(abs(queue[j].iGo-iNow)<iMinMove)} //if((queue[j].iBeVisited==0)&&(queue[j].iGo>=iNow))} //for(j=0;j<iReqNum;j++)if(iNext!=-1){//输出信息摸拟访问请求的磁道cout<<" "<<i+1<<" "<<queue[iNext].iGo<<" "<<abs(queue[iNext].iGo-iNow)<<endl;iSum+=abs(queue[iNext].iGo-iNow);//累加总移动磁道数iNow=queue[iNext].iGo;//移动磁头当前位置为当前访问磁道号queue[iNext].iBeVisited=1;//设置磁道是否已经访问标志为1:已访问} //if(iNext!=-1)else//掉头向外{for(j=0;j<iReqNum;j++)//寻找当前方向上寻道距离最短的未访问磁道号在数组队列queue中的下标{if((queue[j].iBeVisited==0)&&(queue[j].iGo>iNow)){if(abs(queue[j].iGo-iNow)<iMinMove){iNext=j;iMinMove=abs(queue[j].iGo-iNow);}}} //for(j=0;j<iReqNum;j++)//输出信息摸拟访问请求的磁道cout<<".."<<i+1<<"……"<<queue[iNext].iGo<<"…"<<abs(queue[iNext].iGo-iNow)<<endl;iSum+=abs(queue[iNext].iGo-iNow);//累加总移动磁道数iNow=queue[iNext].iGo;//移动磁头当前位置为当前访问磁道号queue[iNext].iBeVisited=1;//设置磁道是否已经访问标志为1:已访问} //if(iNext!=-1)} //for(i=0;i<iReqNum;i++)cout<<endl<<"总调度次数: "<<iReqNum<<endl;cout<<endl<<"总移动磁道数: "<<iSum<<endl;printf("\n平均移动磁道数: %.2f\n\n",(float)iSum / (float)iReqNum);break;default:printf("\n输入错误!!\n\n");return;}//switch(iInput)}运行结果:(2)最短寻道优先调度算法:void SSTF() //最短寻道优先调度算法{Reset();//重置访问标志、磁头当前位置、总移动磁道数cout << endl << "---------------------------------------------" << endl;cout << "最短寻道优先调度算法的调度结果: " << endl << endl;cout << "初始磁道号: " << iStart << endl;cout << "序号下一磁道号移动的磁道数" << endl;int numberend = 0;//已经运行的磁道的数目int size = 0;//当前磁道与某磁道的距离int NewiNow = 0;//记录与当前磁头距离最短的磁道的下标,初始化为0while (numberend != iReqNum)//已经运行的磁道的数目超出最大数目时退出循环{for (int i = 0; i < iReqNum; i++){if (!queue[i].iBeVisited){size = abs(iNow - queue[i].iGo);//初始化当前距离NewiNow = i;//跟新下标break;}}for (int i = 0; i < iReqNum; i++)//循环遍历,在为输出的磁道中寻找与当前磁道最近的磁道{if (!queue[i].iBeVisited&&size > abs(iNow - queue[i].iGo))//如果该磁道没有被访问,且距离小于当前距离{size = abs(iNow - queue[i].iGo);//更新磁道距离NewiNow = i;//跟新下标}}queue[NewiNow].iBeVisited = 1;//标记该磁道已访问iNow = queue[NewiNow].iGo;//移动磁头当前位置为当前访问磁道号iSum += size;//累加总移动磁道数++numberend;//更新已经访问磁道数目//输出信息摸拟访问请求的磁道cout << " " << numberend << " " << iNow << " " << size << endl;}cout << endl << "总调度次数: " << iReqNum << endl;cout << endl << "总移动磁道数: " << iSum << endl;printf("\n平均移动磁道数: %.2f\n\n", (float)iSum / (float)iReqNum);}运行结果分析:(2)最短寻道优先调度算法:实验总结:深刻理解FCFS,最短寻道优先,电梯算法。

驱动调度算法

驱动调度算法

一.模拟电梯调度算法,实现对磁盘的驱动调度二.程序中使用的数据结构及其说明typedefstruct Process//描述进程信息{char name[N]。

//进程名int cyl_num。

//请求的柱面号int tra_num。

//请求的磁道号int rec_num。

//请求的物理记录号int signal。

//标记位}process。

三.源程序及注释pro_struct.h#ifndef PRO_STRUCT_H#define PRO_STRUCT_H#define N 10typedefstruct Process//描述进程信息{char name[N]。

//进程名int cyl_num。

//请求的柱面号int tra_num。

//请求的磁道号int rec_num。

//请求的物理记录号int signal。

//标记位}process。

#endifpro_list.h#ifndef PRO_LIST_H#define PRO_LIST_H#include<iostream>#include<string.h>#include"pro_struct.h"usingnamespace std。

#define M 100void list(int pro_count,int pro_num,process pro[M]>//创建等待进程表b5E2RGbCAP{cout<<"等待的进程数:"。

cin>>pro_num。

if(pro_num>0&&(pro_num+pro_count><=M>//判断要输入的进程数是否合法,输入后是否超出进程等待表所允许的最大值p1EanqFDPw {cout<<"开始输入"<<endl。

磁盘驱动调度算法

磁盘驱动调度算法

磁盘驱动调度算法磁盘驱动调度算法是操作系统中的一种重要机制,用于决定磁盘上的数据访问顺序,提高磁盘的读写效率。

在计算机系统中,磁盘是一种主要的存储介质,而磁盘驱动调度算法则是决定计算机系统如何合理地利用磁盘资源的关键。

磁盘驱动调度算法的目标是通过合理地安排磁盘上的数据访问顺序,最大限度地提高磁盘的读写效率。

在实际应用中,磁盘上的数据往往是分散存储的,即不同的文件、目录等数据被存储在不同的磁盘块中。

因此,当系统需要读取或写入某个文件时,需要将磁头移动到相应的磁道上,然后再进行数据的读取或写入操作。

而磁盘驱动调度算法的任务就是决定磁头的移动顺序,从而提高磁盘的访问效率。

常见的磁盘驱动调度算法有先来先服务(FCFS)、最短寻道时间优先(SSTF)、电梯调度算法(SCAN)、循环扫描算法(C-SCAN)等。

下面将逐一介绍这些算法的特点和应用场景。

1. 先来先服务(FCFS)算法:该算法按照磁盘请求的先后顺序进行调度,即先到达磁盘的请求先被服务。

这种算法简单直接,但由于没有考虑磁盘的物理结构和磁头的移动距离等因素,可能会导致磁盘的平均寻道时间较长。

2. 最短寻道时间优先(SSTF)算法:该算法会选择离当前磁道最近的请求进行服务,从而减少磁头的移动距离,提高磁盘的读写效率。

然而,这种算法可能会出现饥饿现象,即某些请求长时间得不到服务。

3. 电梯调度算法(SCAN):该算法模拟了电梯的运行过程,磁头按照一个方向移动,直到到达磁盘的边界,然后改变方向继续移动。

这种算法能够有效地减少磁头的移动次数,提高磁盘的读写效率。

但由于磁头只能按照一个方向移动,可能会导致某些请求长时间得不到服务。

4. 循环扫描算法(C-SCAN):该算法是电梯调度算法的一种改进,磁头按照一个方向移动,直到到达磁盘的边界,然后立即返回到起始位置,继续移动。

这种算法能够有效地减少磁头的移动距离,提高磁盘的读写效率。

不同的磁盘驱动调度算法适用于不同的应用场景。

模拟电梯调度算法概要

模拟电梯调度算法概要

一、课程设计目的了解驱动调度程序的动态运行过程, 理解和掌握驱动调度的职能。

驱动调度能降低为若干个输入输出请求服务所需的总时间,从而提高系统功能。

二、软硬件环境1.软件配置windows.xp 、 TURBOC2。

2. 硬件配置内存 256; CPU inter pentinum®4 2.80G 赫兹。

三、系统设计及开发过程1. 系统具体设计过程(1.模拟电梯调度算法, 对磁盘进行移臂和旋转调度, 使进程访问磁盘, 他们实现过程是:通过随机函数产生 [0, 1]之间随机数, 判断这个随机数是不是大于 0.5, 是, 则执行驱动调度,否,则执行接受请求(2 . 假定随机数大于 0.5,则执行驱动调度,在屏幕输出当前请求 I/O表中的等待进程, 然后输出选中进程名, 访问的柱面号, 物理记录和当前移臂方向。

(3 . 假定随机数小于 0.5,则执行接受请求。

将输入的进程的物理地址排入等待队列,写入请求I/O表中。

2. 主要数据结构设计为了记录进程访问磁盘请求的情况, 以及进程访问磁盘状态信息, 我们设计了请求 I/O表结构体 askb ,请求 I/O表包括四项int name 进程名 //标志进程的名字;int zmh 柱面号 //当前磁臂所在柱面号;int wj 物理记录 //当前磁臂所在物理记录号;int fx 方向 //移臂方向,向里,向外;用请求 I/O表定义了请求 I/O表 W[1600],全局型变量 M 。

1、私有成员(1、结构体型数组 b[1600]充当等待队列;(2、两个变量 m , n 记录最后访问柱面号,物理记录号(3、变量 cont 记录输入请求的个数;(4、数组 flag[1600]记录移臂方向;(5、 M 是接受请求输入的中间量;(6、 l,h 记录选中进程数2、公有成员(1、 jieshou ( 将输入的请求访问磁盘的进程的进程名,柱面号及物理记录写入请求 I/O表中,变量 g 加 1;(2、 driver( 沿臂移动方向选择离当前旋转或移臂距离最短的等待访问进程(3、 print( 输出当前请求 I/O表中的等待访问进程, 并输出选中的进程名, 访问柱面号,物理记录号3. 算法设计主要函数说明及其流程图函数名 main( 如图 1主程序流程所示。

磁盘调度算法及模拟

磁盘调度算法及模拟

磁盘调度算法及模拟磁盘调度算法是操作系统中用于管理磁盘访问请求的一种机制,其目的是优化磁盘的访问速度和效率。

磁盘调度算法主要考虑如何按照一定的规则来调度磁盘上的读写请求,以尽可能减少磁头的移动距离和等待时间,提高磁盘的访问性能。

常见的磁盘调度算法包括先来先服务(FCFS)、最短寻道时间优先(SSTF)、电梯调度算法(SCAN)、循环扫描算法(C-SCAN)和最短期望时间优先(C-LOOK)等。

1.先来先服务(FCFS)算法:按照请求的顺序处理磁盘访问请求,效率较低。

2.最短寻道时间优先(SSTF)算法:始终选择离当前磁头位置最近的请求进行处理,减少磁头的移动距离。

但容易造成一些请求长时间等待。

3.电梯调度算法(SCAN):磁头按照其中一方向(例如柱面号增大)移动,直到到达磁道的最边缘,然后改变方向继续移动。

这样可以使得距离较远的磁头请求较少等待时间,但在磁头改变方向时可能造成一些请求需要等待。

4.循环扫描算法(C-SCAN):与SCAN类似,但在到达磁道最边缘后,直接返回到最开始的磁道继续扫描。

这样可以减少等待时间,但请求之间可能存在不公平的情况。

5.最短期望时间优先(C-LOOK)算法:磁头按照其中一方向移动,直到扫描完所有请求,然后返回最开始的磁道重新扫描。

这种方式减少了等待时间,并且使请求公平地被处理。

下面对磁盘调度算法进行模拟:假设磁盘上有一系列的读写请求,我们可以随机生成一些磁道号来模拟这些请求。

假设磁头的初始位置在1号磁道,我们可以使用Python编程语言实现一个简单的模拟算法。

```pythonimport random#初始化请求队列request_queue = []for _ in range(10):request_queue.append(random.randint(1, 100))#初始化磁头位置和移动方向head = 1direction = 1#使用SCAN算法进行模拟total_distance = 0while request_queue:#寻找离当前磁头位置最近的请求nearest_request = min(request_queue, key=lambda x: abs(x - head))#计算磁头移动距离,并更新磁头位置distance = abs(nearest_request - head)head = nearest_request#累计移动距离total_distance += distance#处理请求request_queue.remove(nearest_request)#打印相关信息print('磁头移动到磁道{},移动距离为{}'.format(nearest_request, distance))print('总移动距离为:', total_distance)```以上为一个简单的模拟算法,随机生成10个磁道号作为请求,模拟使用SCAN算法进行调度。

磁盘电梯调度实验报告

磁盘电梯调度实验报告

通过本次实验,我们旨在深入了解磁盘电梯调度算法的原理和实现方法,掌握磁盘调度在提高系统性能中的作用。

通过对磁盘电梯调度算法的模拟实现,观察和分析不同调度策略对磁盘访问效率的影响,从而加深对磁盘调度算法的理解。

二、实验环境实验软件:Windows 10操作系统实验工具:Visual Studio 2019实验平台:个人计算机三、实验原理磁盘电梯调度算法是一种常用的磁盘调度策略,其原理类似于电梯的工作方式。

在磁盘调度过程中,磁头从磁盘的一个柱面移动到另一个柱面,就像电梯从一层楼移动到另一层楼。

磁盘电梯调度算法的目标是尽可能减少磁头移动的距离,从而提高磁盘访问效率。

四、实验内容1. FCFS(先来先服务)调度算法FCFS算法按照请求的顺序服务磁盘请求,即先到达的请求先被服务。

该算法实现简单,但效率较低,容易产生“饥饿”现象。

2. SSTF(最短寻找时间优先)调度算法SSTF算法选择距离磁头最近的请求进行服务,以减少磁头移动的距离。

该算法在请求比较均匀时效率较高,但在请求集中时可能会产生“局部最优”问题。

3. SCAN(扫描)调度算法SCAN算法从磁头当前位置开始,向一个方向移动,直到该方向的请求都被服务,然后反向移动。

该算法在请求比较分散时效率较高,但可能会产生“振荡”现象。

4. C-SCAN(循环扫描)调度算法C-SCAN算法与SCAN算法类似,但在到达磁盘末尾时,磁头不返回,而是直接移动到磁盘起始位置,然后继续向一个方向移动。

该算法可以避免“振荡”现象,但可能会产生“局部最优”问题。

1. 初始化创建一个磁盘调度模拟器,包括磁头位置、请求队列、磁盘分区等信息。

2. 调度算法实现根据选择的调度算法,实现相应的磁盘调度策略。

3. 模拟运行输入一系列磁盘请求,按照调度算法进行服务,并记录磁头移动距离、服务时间等指标。

4. 结果分析对不同调度算法的实验结果进行分析,比较它们的性能差异。

六、实验结果与分析1. FCFS算法FCFS算法在实验中表现较差,磁头移动距离较长,服务时间较长。

模拟电梯调度算法-实现对磁盘的驱动调度。

模拟电梯调度算法-实现对磁盘的驱动调度。

模拟电梯调度算法-实现对磁盘的驱动调度。

案场各岗位服务流程销售大厅服务岗:1、销售大厅服务岗岗位职责:1)为来访客户提供全程的休息区域及饮品;2)保持销售区域台面整洁;3)及时补足销售大厅物资,如糖果或杂志等;4)收集客户意见、建议及现场问题点;2、销售大厅服务岗工作及服务流程阶段工作及服务流程班前阶段1)自检仪容仪表以饱满的精神面貌进入工作区域2)检查使用工具及销售大厅物资情况,异常情况及时登记并报告上级。

班中工作程序服务流程行为规范迎接指引递阅资料上饮品(糕点)添加茶水工作要求1)眼神关注客人,当客人距3米距离时,应主动跨出自己的位置迎宾,然后侯客迎询问客户送客户注意事项15度鞠躬微笑问候:“您好!欢迎光临!”2)在客人前方1-2米距离领位,指引请客人向休息区,在客人入座后问客人对座位是否满意:“您好!请问坐这儿可以吗?”得到同意后为客人拉椅入座“好的,请入座!”3)若客人无置业顾问陪同,可询问:请问您有专属的置业顾问吗?,为客人取阅项目资料,并礼貌的告知请客人稍等,置业顾问会很快过来介绍,同时请置业顾问关注该客人;4)问候的起始语应为“先生-小姐-女士早上好,这里是XX销售中心,这边请”5)问候时间段为8:30-11:30 早上好11:30-14:30 中午好 14:30-18:00下午好6)关注客人物品,如物品较多,则主动询问是否需要帮助(如拾到物品须两名人员在场方能打开,提示客人注意贵重物品);7)在满座位的情况下,须先向客人致歉,在请其到沙盘区进行观摩稍作等待;阶段工作及服务流程班中工作程序工作要求注意事项饮料(糕点服务)1)在所有饮料(糕点)服务中必须使用托盘;2)所有饮料服务均已“对不起,打扰一下,请问您需要什么饮品”为起始;3)服务方向:从客人的右面服务;4)当客人的饮料杯中只剩三分之一时,必须询问客人是否需要再添一杯,在二次服务中特别注意瓶口绝对不可以与客人使用的杯子接触;5)在客人再次需要饮料时必须更换杯子;下班程序1)检查使用的工具及销售案场物资情况,异常情况及时记录并报告上级领导;2)填写物资领用申请表并整理客户意见;3)参加班后总结会;4)积极配合销售人员的接待工作,如果下班时间已经到,必须待客人离开后下班;1.3.3.3吧台服务岗1.3.3.3.1吧台服务岗岗位职责1)为来访的客人提供全程的休息及饮品服务;2)保持吧台区域的整洁;3)饮品使用的器皿必须消毒;4)及时补充吧台物资;5)收集客户意见、建议及问题点;1.3.3.3.2吧台服务岗工作及流程阶段工作及服务流程班前阶段1)自检仪容仪表以饱满的精神面貌进入工作区域2)检查使用工具及销售大厅物资情况,异常情况及时登记并报告上级。

电梯调度算法

电梯调度算法

1.实验目的通过该实验,掌握电梯调度算法的设计思路及实现代码。

2.实验内容1.模拟一个磁盘调度算法2.要求能够模拟电梯算法磁盘调度算法3.输入一组作业的磁道请求4.输出为该算法执行时的磁头移动轨迹及移动臂的移动距离3.设计思路用顺序表按从小到大的顺序依次存储用户输入的请求柱面号,读写顺序分为由外到内和由内到外,若为由外到内,则现将磁头正在操作的柱面号与顺序表中的柱面号依次比较,找到比它大的第一个元素,记录下标,从该元素开始依次向后输出,待输出最后一个元素后,则从记录下标的前一个元素,一次向前输出;若顺序为由内向外,则操作相反。

4.关键代码#include<stdio.h>#define MAXSIZE 100typedef struct ZM{int a[MAXSIZE];int size;}zhumian;void init(zhumian *slt){slt->size=0;}void insert(zhumian *slt,int x){int j,i=0;if(slt->size==MAXSIZE){printf("\n柱面号已满!无法插入!");exit(1);}if(slt->size==0){slt->a[0]=x;slt->size++;}else{while(i<slt->size && slt->a[i]<=x){i++;}for(j=slt->size;j>i;j--){slt->a[j]=slt->a[j-1];}slt->a[i]=x;slt->size++;}}main(){zhumian slt;int x,choice,num,i,j,distance;printf("磁盘共200个柱面,编号为0-199");printf("\n\n请依次输入请求的柱面号('-1'表示结束):");scanf("%d",&x);init(&slt);while(x!=-1){insert(&slt,x);scanf("%d",&x);}printf("\n请选择读写顺序:\n");printf("\n1.由外向内( 0->199 )\n");printf("\n2.由内向外( 199->0 )\n\n您的选择为:");scanf("%d",&choice);printf("\n请输入磁头正在读写的柱面号:");scanf("%d",&num);if(choice==1){i=0;while(i<slt.size && slt.a[i]<num){i++;}printf("\n电梯调度算法的次序为:");for(j=i;j<slt.size;j++){printf("%d ",slt.a[j]);}for(j=i-1;j>=0;j--){printf("%d ",slt.a[j]);}distance=(slt.a[slt.size-1]-num)+(slt.a[slt.size-1]-slt.a[0]);printf("\n\n移动臂移动的距离为:%d\n",distance);}if(choice==2){i=0;while(i<slt.size && slt.a[i]<num){i++;}printf("\n电梯调度算法的次序为:");for(j=i-1;j>=0;j--){printf("%d ",slt.a[j]);}for(j=i;j<slt.size;j++){printf("%d ",slt.a[j]);}distance=(slt.a[slt.size-1]-slt.a[0])+(num-slt.a[0]);printf("\n\n移动臂移动的距离为:%d\n",distance);}}5.运行结果。

模拟电梯调度算法,实现对磁盘的驱动调度。

模拟电梯调度算法,实现对磁盘的驱动调度。

操作系统实验(第三次)一、实验内容模拟电梯调度算法,实现对磁盘的驱动调度。

[提示](1当有多个进程提出输入输出要求而处于等待状态时,可用电梯调度算法从若干个等待访问者中选择一个进程,让它访问磁盘。

选择访问者的工作由“驱动调度”进程来完成。

由于磁盘与处理器是可以并行工作的、所以当磁盘在作为一个进程服务时,占有处理器的另一进程可以提出使用磁盘的要求,也就是说,系统能动态地接收新的输入输出请求。

为了模拟这种情况,在本实验中设置了一个“接收请求”进程。

“驱动调度”进程和“接收请求”进程能否占有处理器运行,取决于磁盘的结束中断信号和处理器调度策略。

在实验中可用随机数来模拟确定这两个进程的运行顺序,以代替中断四、处理和处理器调度选择的过程。

因而,程序的结构可参考图3—1(2)“接收请求”进程建立一张“请求I/O”表,指出访问磁盘的进程要求访问的物理地址,表的格式为:(3)这种调度策略能使移动臂的移动频率极小,从而提高系统效率。

用电梯调度算法实现驱动调度的模拟算法如图3-3。

(4)图3-1中的初始化工作包括,初始化“请求I/O”表,置当前移臂方向为里移;置当前位置为0号柱面,0号物理记录。

程序运行前可假定“请求I/O”表中已经有如干个进程等待访问磁盘。

在模拟实验中,当选中一个进程可以访问磁盘时,并不实际地启动磁盘,而用显示:“请求I/O”表;当前移臂方向;当前柱面号,物理记录号来代替图3-3中的“启动磁盘”这项工作。

(1)程序中使用的数据结构及其说明。

constintPCB=100;//定义100个进程intpcbs_num=0;//记录当前io表的进程个数{(2(6)#include<cstdlib>(7)#include<fstream>(8)usingnamespace std;(9)constint PCB=100;//定义100个进程(10)int pcbs_num=0;//记录当前io表的进程个数(11)typedefstruct process//请求io表(12){(13)char pname[10];//进程名(14)int Cylinder;//柱面号(15)int Track;//磁道号(16)int Record;//物理记录号(31){(32)}(33)cout<<i<<endl;(34)return i;(35)}(36)void accept()//接受请求模拟算法(37){(38)cout<<"输入进程名和物理地址(柱面号,磁道号,物理记录号)"<<endl;(39)cin>>pcbs[pcbs_num].pname>>pcbs[pcbs_num].Cylinder>>pcbs[pcbs_num].Track>>pcbs[pcbs_num].Recor d;(40)pcbs_num++;(55){(56)if(pcbs[i].Cylinder==cylinder)(57){(58)a=pcbs[i].Record-record;(59)if(a<0){a=a+8;}(60)if(a<t)(61){(62)t=a;k=i;(63)}(64)}(65)}(80){(81)if(pcbs[i].Cylinder==num&&pcbs[i].Record<t) (82){(83)t=pcbs[i].Record;a=i;(84)}(85)}(86)return a;(87)}(88)int Cylinder_max1(int cylinder)(89){(90)int t=199,i,b=0,c=0;(105){(106)t=abs(pcbs[i].Cylinder-cylinder); (107)}(108)}(109)num=cylinder-t;t=8;//物理块号相差最大为7(110)for(i=0;i<pcbs_num;i++)(111){(112)if(pcbs[i].Cylinder==num&&pcbs[i].Record<t)(113){(114)t=pcbs[i].Record;a=i;(115)}(130)cout<<setfill('')<<setw(6)<<pcbs[i].pname<<setfill('')<<setw(8)<<pcbs[i].Cylinder<<setfill('')<<setw(8) <<pcbs[i].Track<<setfill('')<<setw(10)<<pcbs[i].Record<<endl;(131)}(132)}(133)void print_scan(bool x)(134){(135)cout<<"选中的:"<<endl;cout<<"进程名"<<"柱面号"<<"磁道号"<<"物理记录号"<<"方向"<<endl;cout<<setfill('')<<setw(6)<<a.pname<<setfill('')<<setw(8)<<a.Cylinder<<setfill('')<<setw(10)<<a.Tra ck<<setfill('')<<setw(10)<<a.Record<<setfill('')<<setw(6)<<x<<endl;(136)}(137)int SCAN()//驱动调度电梯调度模拟算法(153)if(pcbs[Cylinder_e()].Cylinder==a.Cylinder)//选择能使旋转距离最短的访问者(154){(155)scan=Cylinder_near(a.Cylinder,a.Record);//选择当前柱面号的访问者中最近的(156)if(pcbs[scan].Cylinder<a.Cylinder)(157){(158)way=0;(159)}(160)else way=1;(161)}(162)else(163){(178){(179)scan=Cylinder_max(a.Cylinder); (180)way=1;(181)}(182)}(183)}a=pcbs[scan];(184)delete_scan(scan);//删除pcbs[scan](185)print_scan(way);//打印(186)return1;(187)}(188)}(203)cout<<"继续?(y/n)"<<endl; (204)cin>>y;(205)}(206)}(207)void main()(208){(209)work();(210) }(4)打印驱动调度进程每次选择访问请求前的“请求I/O”表以及每次选中的进程名、访问的柱面号、物理记录号和当前移臂方向(用up代表里移,down代表外移。

模拟实现磁盘调度算法

模拟实现磁盘调度算法

模拟实现磁盘调度算法磁盘调度算法是操作系统中用于确定磁盘驱动器上的读写操作顺序的一种方法。

磁盘调度算法的目标是尽量提高磁盘的利用率和性能,减少磁盘的寻道时间和旋转延迟。

在实现磁盘调度算法之前,让我们先了解一些与磁盘调度相关的概念。

1.磁盘寻道时间:磁盘读/写头从当前磁道移动到目标磁道所需的时间。

寻道时间越短,磁盘访问速度越快。

2.磁盘旋转延迟:磁盘读/写头等待目标扇区旋转到读/写位置所需的时间。

旋转延迟取决于磁盘转速,常用转速为7200转/分钟或更高。

3.请求队列:保存待执行的读/写请求的队列。

4.当前磁道位置:磁盘读/写头当前所在的磁道。

5.下一个请求:即将被执行的读/写请求。

下面我们将模拟实现三种常见的磁盘调度算法:先来先服务(FCFS)、最短寻道时间优先(SSTF)和电梯(LOOK)算法。

1.先来先服务(FCFS)算法:FCFS算法按照请求的先后顺序进行磁盘访问,即先到先服务。

当程序提交读/写请求时,请求按照提交的顺序加入到请求队列中,然后按照队列中的顺序依次执行。

这种算法简单直接,但可能导致磁盘寻道时间较长。

缺点:容易产生“响应时间过长”和“饥饿”现象。

2.最短寻道时间优先(SSTF)算法:SSTF算法每次选择与当前磁头位置最近的磁道进行磁盘访问。

算法会根据当前磁头位置和请求队列中的请求位置计算寻道时间,选择寻道时间最短的请求作为下一个请求。

这种算法可以找到离当前磁头位置最近的请求,有效减少寻道时间。

但可能会导致一些请求一直等待。

3.电梯(LOOK)算法:LOOK算法模拟了电梯的运行方式。

它按照一个方向来执行读/写请求,直到请求队列中没有该方向上的请求,然后改变运行方向,继续执行另一方向上的请求。

LOOK算法是一种比较公平的磁盘调度算法,可以减少寻道时间和旋转延迟。

在实际的磁盘调度算法实现中,我们通常需要实现请求队列的管理、寻道时间计算、磁头位置更新等功能。

可以使用队列来管理请求队列,使用寻道算法计算寻道时间,使用函数来模拟磁头位置的更新。

驱动调度

驱动调度

驱动调度1 实验目的磁盘是一种高速、大容量、旋转型、可直接存取的存储设备。

它作为计算机系统的辅助存储器,担负着繁重的输入输出任务、在多道程序设计系统中,往往同时会有若干个要求访问磁盘的输入输出请求等待处理。

系统可采用一种策略,尽可能按最佳次序执行要求访问磁盘的诸输入输出请求。

这就叫驱动调度,使用的算法称为驱动调度算法。

驱动调度能降低为若干个输入输出请求服务所需的总时间,从而提高系统效率。

2 设置初始条件1、操作系统:windows2、程序设计语言:C++3 功能描述模拟电梯调度算法,实现对磁盘的驱动调度。

4 方案论证4.1 数据结构设计typedef struct Process //描述进程信息{char name[N]; //进程名int cyl_num; //柱面号int tra_num; //磁道号int rec_num; //物理记录号int signal; //标记,用以判断结构体数组中该元素是否有效}process;4.2 算法设计函数模块各函数调用关系如图1所示,箭头指向被调用的函数主函数随机数函数接收请求函数电梯调度函数旋转调度函数移臂调度函数图1 函数调用关系流程图各函数功能及流程图如下:4.2.1主函数:void main()函数功能:显示提示信息,初始化进程数组,根据随机数的值选择调用驱动调度和接收请求或者选择继续和退出程序入口参数:无出口参数:无流程图:如图2所示图2 主函数流程图输出提示信息输入一个随机数随机数>0.5?初始化进程请求表(实际为进程的结构体数组)驱动调度接收请求继续?结束是否是否4.2.2随机数函数:float Ran_Num() 函数功能:接收随机数 入口参数:无出口参数:接收进来的随机数 流程图:无4.2.3接收请求函数:void list(int pro_count,int pro_num,process pro[M]) 函数功能:存放输入的进程信息,创建等待进程列表 入口参数:初始化后的进程数组 出口参数:无 流程图:如图3所示是否返回当前进程数组能存入?输入进程信息输入信息有错?i=0i++第i 个元素有效?已输入的进程数小于要输入的进程数图3 接收请求流程图是否是否是否是否有请求?输入要输入的进程个数已输入的进程数+14.2.4旋转调度函数:void cir_sec(process pro[M])函数功能: 如果有请求与当前柱面号相同,进行旋转调度,选择旋转距离最小的进程入口参数:部分全局变量及进程数组 出口参数:选择的数组元素编号流程图:如图4所示开始选择当前的访问进程结束当前访问者旋转距离小于最小旋转距离否是图4 旋转调度流程图4.2.5移臂调度函数:void mov_sec(process pro[M])函数功能:没有与当前柱面号相同的访问请求时,进行移臂调度 入口参数:进程数组出口参数:选择的数组元素编号 流程图:如图5所示当前移臂方向是向里移有比当前柱面号大的访问请求有比当前柱面号小的访问请求从大于当前柱面号的访问请求中选择一个最小者置当前移臂方向为向外移置当前移臂方向为向里移从小于当前柱面号的访问请求中选择一个最小者是否否否是是开始旋转调度结束图5 移臂调度流程图4.2.6驱动调度函数:void dri_sch(int pro_count,process pro[M] ) 函数功能:进行进程调度,按照电梯调度算法选择进程入口参数:当前有效进程数、进程数组出口参数:无流程图:如图6所示登记当前位置:柱面号,物理记录号被选中者退出“请求I/O 表”结束输出选择的进程开始查“请求I/O 表”有等待访问者输出“请求I/O 表”有请求与当前柱面号相同旋转调度移臂调度是否是否图6 驱动调度流程图5 设计结果与分析 5.1运行结果如下图7 初始状态图8 输入5个进程的相关信息图9 第一次选择后结果图10 第二次选择后结果图11 第三次选择后结果图12 第四次选择后结果图13 第五次选择后,进程等待表为空图14 再输入3个进程及相关信息图15 再次输入后第一次选择图16 再次输入后第二次选择图17 第三次选择后等待表为空,选择退出5.2 结果分析5.2.1初始状态,结果如图7所示5.2.2输入0.4,输入进程数据并选择继续,结果如图8所示5.2.3重复选择继续,输入0.6进行驱动调度直到等待进程表为空,结果如图9~图13所示第一次选择P5第二次选择P3第三次选择P1第四次选择P4第五次选择P2,当前等待表为空5.2.4选择继续,输入0.4,再输入3个进程,结果如图14所示5.2.5重复选择继续进行驱动调度至等待进程表为空,然后选择退出,结果如图15~图17所示第一次选择P8第二次选择P6第三次选择P7,当前等待表为空,选择退出6 课设总结1、通过设计数据结构进程访问磁盘,我进一步了解了磁盘存储器的物理结构,对电梯算法有深入的了解。

操作系统课程设计题目与要求1

操作系统课程设计题目与要求1

操作系统课程设计题目与要求一、课程设计要求:1.根据每道题的人数选定题目。

2.分析设计要求,给出解决方案,建立必要的数据结构,然后设计总体流程(包括界面)、详细设计必要的算法,并最终显示结果。

基于WINDOWS或LINUX操作系统都可以,用何种编程语言都有可以。

3.提交设计报告,包括设计要求、设计思想流程、设计所涉及的主要数据结构、程序清单、运行结果、设计心得、参考资料等。

4.严禁抄袭,复制设计内容,查出后相关同学设计成绩以零分处理。

5.所提交源程序应是能够运行通过的完整程序。

6.课程设计参考评分标准:设计思想说明(10分);数据结构的说明(6分);各模块的算法流程图(10分);程序清单:注意加注释(包含关键字、方法、变量等),在每个模块前加注释;(共70分,其中书面源程序占35分,实验的检查结果、程序的运行情况占35分)体会,总结及体会建议(4分)。

二、设计题目1.Windows多线程控制台程序(1人)目的:学习和掌握如何编写Windows多线程控制台程序。

通过编写程序,加深对进程和线程关系的理解,掌握多线程程序的执行和编写技巧。

设计要求:写一个单进程多线程的Windows控制台程序,该程序在一个进程内建立N个线程来执行指定的任务。

N由命令行传递给系统。

Win32控制台程序中,主函数的格式如:Void main(int argc,char *argv[]),可以获取命令行参数。

通过VC++“工程/设置”的C/C++属性页设置应用程序为“MTD”多线程。

利用win32 API CreateThread()来生成线程。

2.睡眠理发师问题(2人)目的:了解信号量机制,了解并掌握进程同步和互斥机制,熟悉信号量的操作函数,利用信号量实现对共享资源的控制。

设计要求:(1)编写程序实现理发师与顾客进程的同步。

问题描述:这是一种经典的IPC问题,理发店有一位理发师,一把理发椅和n把用来等候理发的椅子。

如果没有顾客,则理发师在理发椅上睡觉,顾客理来时,如理发师闲则理发,否则如有空椅则坐等,没有空椅则离开,编写程序实现理发师和顾客程序,实现进程控制,要求不能出现竞争。

电梯调度算法实验报告

电梯调度算法实验报告
-2-源自作系统实验报告课程 学号 姓名
操作系统
日期
实验项目 名称
磁盘调度
cout<<"-----------------------------------------------"<<endl;
cout<<"要访问的磁道号为:";
for(i=0;i<10;i++) {cout<<p[i]<<" "; if (i==9){cout<<endl;}
cout<<"**************** 测试完成*******************"<<endl;
-3-
操作系统实验报告
课程 学号 姓名
操作系统
cout<<endl; cout<<endl;
日期
实验项目 名称
磁盘调度
//********************分析磁头扫描位置******************************// cout<<"************此时磁头正在自里向外移动扫描*****************"<<endl; for(int u=a,q=1;u>=0;u--,q++){
}
cout<<"当 前磁头位置 为:"<<P2<<endl; cout<<"----------------------------------------------"<<endl;
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

操作系统实验(第三次)一、实验内容模拟电梯调度算法,实现对磁盘的驱动调度。

二、实验目的磁盘是一种高速、大容量、旋转型、可直接存取的存储设备。

它作为计算机系统的辅助存储器,担负着繁重的输入输出任务、在多道程序设计系统中,往往同时会有若干个要求访问磁盘的输入输出请求等待处理。

系统可采用一种策略,尽可能按最佳次序执行要求访问磁盘的诸输入输出请求。

这就叫驱动调度,使用的算法称为驱动调度算法。

驱动调度能降低为若干个输入输出请求服务所需的总时间,从而提高系统效率。

本实验要求学生模拟设计一个驱动调度程序,观察驱动调度程序的动态运行过程。

通过实验使学生理解和掌握驱动调度的职能。

三、实验题目模拟电梯调度算法,对磁盘进行移臂和旋转调度。

[提示]:(1)磁盘是可供多个进程共享的存储设备,但一个磁盘每时刻只能为一个进程服务。

当有进程在访问某个磁盘时,其他想访问该磁盘的进程必须等待,直到磁盘一次工作结束。

当有多个进程提出输入输出要求而处于等待状态时,可用电梯调度算法从若干个等待访问者中选择一个进程,让它访问磁盘。

选择访问者的工作由“驱动调度”进程来完成。

由于磁盘与处理器是可以并行工作的、所以当磁盘在作为一个进程服务时,占有处理器的另一进程可以提出使用磁盘的要求,也就是说,系统能动态地接收新的输入输出请求。

为了模拟这种情况,在本实验中设置了一个“接收请求”进程。

“驱动调度”进程和“接收请求”进程能否占有处理器运行,取决于磁盘的结束中断信号和处理器调度策略。

在实验中可用随机数来模拟确定这两个进程的运行顺序,以代替中断四、处理和处理器调度选择的过程。

因而,程序的结构可参考图3—1(2)“接收请求”进程建立一张“请求I/O”表,指出访问磁盘的进程要求访问的物理地址,表的格式为:假定某个磁盘组共有200 个柱面,由外向里顺序编号(0—199),每个柱面上有20 个磁道,编号为0—19,每个磁道分成8 个物理记录,编号0—7。

进程访问磁盘的物理地址可以用键盘输入的方法模拟得到。

图3—2 是“接收请求”进程的模拟算法。

在实际的系统中必须把等待访问磁盘的进程排入等待列队,由于本实验模拟驱动调度,为简单起见,在实验中可免去队列管理部分,故设计程序时可不考虑“进程排入等待队列”的工作。

(3)“驱动调度”进程的功能是查“请求I/O”表,当有等待访问磁盘的进程时,按电梯调度算法从中选择一个等待访问者,按该进程指定的磁盘物理地址启动磁盘为其服务。

对移动臂磁盘来说,驱动调度分移臂调度和旋转调度。

电梯调度算法的调度策略是与移动臂的移动方向和移动臂的当前位子有关的,所以每次启动磁盘时都应登记移动臂方向和当前位子。

电梯调度算法是一种简单而实用的驱动调度方法,这种调度策略总是优先选择与当前柱面号相同的访问请求,从这些请求中再选择一个能使旋转距离最短的等待访问者。

如果没有与当前柱面号相同的访问请求,则根据移臂方向来选择,每次总是沿臂移动方向选择一个与当前柱面号最近的访问请求,若沿这个方向没有访问请求时,就改变臂的移动方向。

这种调度策略能使移动臂的移动频率极小,从而提高系统效率。

用电梯调度算法实现驱动调度的模拟算法如图3-3。

(4)图3-1 中的初始化工作包括,初始化“请求I/O”表,置当前移臂方向为里移;置当前位置为0 号柱面,0 号物理记录。

程序运行前可假定“请求I/O”表中已经有如干个进程等待访问磁盘。

在模拟实验中,当选中一个进程可以访问磁盘时,并不实际地启动磁盘,而用显示:“请求I/O”表;当前移臂方向;当前柱面号,物理记录号来代替图3-3 中的“启动磁盘”这项工作。

(1)程序中使用的数据结构及其说明。

const int PCB=100; //定义100个进程int pcbs_num=0; //记录当前io表的进程个数typedef struct process //请求io表{char pname[10]; //进程名int Cylinder; //柱面号int Track; //磁道号int Record; //物理记录号int Way;}PROCESS;PROCESS pcbs[PCB];PROCESS a; //记录当前位置(柱面号、物理记录号)采用带头节点的循环链表存(2)打印一份源程序并附上注释。

(3)#include<iostream>(4)#include<iomanip>(5)#include<stdio.h>(6)#include<cstdlib>(7)#include<fstream>(8)using namespace std;(9)const int PCB = 100; //定义100个进程(10)int pcbs_num = 0; //记录当前io表的进程个数(11)typedef struct process//请求io表(12){(13)char pname[10]; //进程名(14)int Cylinder; //柱面号(15)int Track; //磁道号(16)int Record; //物理记录号(17)int Way;(18)}PROCESS;(19)PROCESS pcbs[PCB];(20)PROCESS a;(21)void init_a() //设置当前位置(22){(23) a.Cylinder = 4;(24) a.Track = 0;(25) a.Record = 0;(26)}(27)int count_PN() //记录进程总数(28){(29)int i;(30)for (i = 0; pcbs[i].Cylinder != NULL; i++)(31){(32)}(33)cout << i << endl;(34)return i;(35)}(36)void accept() //接受请求模拟算法(37){(38)cout << "输入进程名和物理地址(柱面号,磁道号,物理记录号)" << endl;(39)cin >> pcbs[pcbs_num].pname >> pcbs[pcbs_num].Cylinder >>pcbs[pcbs_num].Track >> pcbs[pcbs_num].Record;(40)pcbs_num++;(41)}(42)int Cylinder_e() //判断柱面号相等(43){(44)for (int i = 0; i<pcbs_num; i++)(45){(46)if (pcbs[i].Cylinder == a.Cylinder)(47)return i;(48)}(49)return 0;(50)}(51)int Cylinder_near(int cylinder, int record) ////选择当前柱面号的访问者中物理块号最近的(52){(53)int t = 8, a, k;(54)for (int i = 0; i<pcbs_num; i++)(55){(56)if (pcbs[i].Cylinder == cylinder)(57){(58) a = pcbs[i].Record - record;(59)if (a<0){ a = a + 8; }(60)if (a<t)(61){(62)t = a; k = i;(63)}(64)}(65)}(66)return k;(67)}(68)int Cylinder_max(int cylinder) //选择比当前柱面号大的请求中柱面号最小的(69){(70)int num, t = 199, i, a = 0, b = 0;(71)for (i = 0; i < pcbs_num; i++)(72){(73)if((abs(pcbs[i].Cylinder - cylinder))<t && pcbs[i].Cylinder > cylinder) (74){(75)t = abs(pcbs[i].Cylinder - cylinder);(76)}(77)} num = cylinder + t; //选择的柱面号(78)t = 8; //物理块号最大相差7(79)for (i = 0; i<pcbs_num; i++)(80){(81)if (pcbs[i].Cylinder == num &&pcbs[i].Record < t)(82){(83)t = pcbs[i].Record; a = i;(84)}(85)}(86)return a;(87)}(88)int Cylinder_max1(int cylinder)(89){(90)int t = 199, i, b = 0, c = 0;(91)for (i = 0; i<pcbs_num; i++)(92){(93)if((abs(pcbs[i].Cylinder - cylinder))>b && pcbs[i].Cylinder > cylinder) (94){(95) b = abs(pcbs[i].Cylinder - cylinder);(96)}(97)}(98)return b;(99)}(100)int Cylinder_min(int cylinder) //选择比当前柱面号小的请求中柱面号最大的(101){(102)int num, t = 199, i, a = 0; for (i = 0; i < pcbs_num; i++)(103){(104)if((abs(pcbs[i].Cylinder - cylinder))<t && pcbs[i].Cylinder < cylinder) (105){(106)t = abs(pcbs[i].Cylinder - cylinder);(107)}(108)}(109)num = cylinder - t; t = 8; //物理块号相差最大为7(110)for (i = 0; i < pcbs_num; i++)(111){(112)if (pcbs[i].Cylinder == num && pcbs[i].Record <t)(113){(114)t = pcbs[i].Record; a = i;(115)}(116)}(117)return a; //返回柱面号小的请求中柱面号最大的下标(118)}(119)void delete_scan(int x)(120){(121)for (int i = x; i<pcbs_num; i++)(122)pcbs[i] = pcbs[i + 1]; pcbs_num--;(123)}(124)void print_io() //打印请求io表(125){(126)cout << "输出请求i/o表:" << endl;(127)cout << "进程名" << " 柱面号" << " 磁道号" << " 物理记录号" << endl;(128)for (int i = 0; i<pcbs_num; i++)(129){(130)cout << setfill(' ') << setw(6) << pcbs[i].pname << setfill(' ') << setw(8) << pcbs[i].Cylinder << setfill(' ') << setw(8) << pcbs[i].Track << setfill(' ') << setw(10) << pcbs[i].Record << endl;(131)}(132)}(133)void print_scan(bool x)(134){(135)cout << "选中的:"<< endl; cout << "进程名"<< " 柱面号"<< " 磁道号"<< " 物理记录号"<< " 方向"<< endl; cout << setfill(' ') << setw(6) << a.pname << setfill(' ') << setw(8) << a.Cylinder << setfill(' ') << setw(10) << a.Track << setfill(' ') << setw(10) << a.Record << setfill(' ') << setw(6) << x << endl;(136)}(137)int SCAN() //驱动调度电梯调度模拟算法(138){(139)print_io(); //打印io表(140)int scan;(141)int scan1;//scan为选择的进程的编号(142)bool way = 1; //方向 0=out 1=in(143)if (a.Cylinder == NULL)(144){(145)init_a();(146)}(147)if (pcbs_num == 0)(148){(149)cout << "无等待访问者" << endl; return 0;(150)}(151)else(152){(153)if (pcbs[Cylinder_e()].Cylinder == a.Cylinder) //选择能使旋转距离最短的访问者(154){(155)scan = Cylinder_near(a.Cylinder, a.Record);//选择当前柱面号的访问者中最近的(156)if (pcbs[scan].Cylinder<a.Cylinder)(157){(158)way = 0;(159)}(160)else way = 1;(161)}(162)else(163){(164)if (way == 1)(165){(166)scan = Cylinder_max(a.Cylinder); //选择比当前柱面号大的请求中物理块号最小的(167)scan1 = Cylinder_max1(a.Cylinder);(168)if (scan == scan1)(169){(170)scan = Cylinder_min(a.Cylinder); //选择比当前柱面号小的请求中物理块号最大的(171)way = 0;(172)}(173)}(174)else(175){(176)scan = Cylinder_min(a.Cylinder);(177)if (scan == 0)(178){(179)scan = Cylinder_max(a.Cylinder);(180)way = 1;(181)}(182)}(183)} a = pcbs[scan];(184)delete_scan(scan); //删除pcbs[scan](185)print_scan(way); //打印(186)return 1;(187)}(188)}(189)void work()//初始化(190){(191)float n; char y = 'y'; while (y == 'y' || y == 'Y')(192){(193)cout << "输入在[0,1]区间内的一个随机数" << endl;(194)cin >> n;(195)if (n>0.5)(196){(197)SCAN(); //驱动调度(198)}(199)else(200){(201)accept(); //接受请求(202)}(203)cout << "继续?(y/n)" << endl;(204)cin >> y;(205)}(206)}(207)void main()(208){(209)work();(210) }(4)打印驱动调度进程每次选择访问请求前的“请求I/O”表以及每次选中的进程名、访问的柱面号、物理记录号和当前移臂方向(用up 代表里移,down 代表外移。

相关文档
最新文档