操作系统实验六

实验内容

本实验通过编程模拟实现几种常见的磁盘调度算法

简直可怕,怎么可能写出来磁盘调度算法啊喂!算法实现倒还好说,就是一个排序算法。但是!访问的柱面就是随机生成的所以还要写iterator?!这里简单描述一下各种磁盘调度算法。

例:假定某磁盘共有200个柱面,编号为0-199,如果在为访问143号柱面的请求者服务后,当前正在为访问125号柱面的请求服务,同时有若干请求者在等待服务,它们每次要访问的柱面号为 86,147,91,177,94,150,102,175,130

1、先来先服务算法(FCFS)First Come First Service
这是一种比较简单的磁盘调度算法。它根据进程请求访问磁盘的先后次序进行调度。此算法的优点是公平、简单,且每个进程的请求都能依次得到处理,不会出现某一进程的请求长期得不到满足的情况。此算法由于未对寻道进行优化,在对磁盘的访问请求比较多的情况下,此算法将降低设备服务的吞吐量,致使平均寻道时间可能较长,但各进程得到服务的响应时间的变化幅度较小。
先来先服务 (125)86.147.91.177.94.150.102.175.130

2、最短寻道时间优先算法(SSTF) Shortest Seek Time First
该算法选择这样的进程,其要求访问的磁道与当前磁头所在的磁道距离最近,以使每次的寻道时间最短,该算法可以得到比较好的吞吐量,但却不能保证平均寻道时间最短。其缺点是对用户的服务请求的响应机会不是均等的,因而导致响应时间的变化幅度很大。在服务请求很多的情况下,对内外边缘磁道的请求将会无限期的被延迟,有些请求的响应时间将不可预期。
最短寻道时间优先(125)130.147.150.175.177.102.94.91.86

3、扫描算法(SCAN)电梯调度
扫描算法不仅考虑到欲访问的磁道与当前磁道的距离,更优先考虑的是磁头的当前移动方向。例如,当磁头正在自里向外移动时,扫描算法所选择的下一个访问对象应是其欲访问的磁道既在当前磁道之外,又是距离最近的。这样自里向外地访问,直到再无更外的磁道需要访问才将磁臂换向,自外向里移动。这时,同样也是每次选择这样的进程来调度,即其要访问的磁道,在当前磁道之内,从而避免了饥饿现象的出现。由于这种算法中磁头移动的规律颇似电梯的运行,故又称为电梯调度算法。此算法基本上克服了最短寻道时间优先算法的服务集中于中间磁道和响应时间变化比较大的缺点,而具有最短寻道时间优先算法的优点即吞吐量较大,平均响应时间较小,但由于是摆动式的扫描方法,两侧磁道被访问的频率仍低于中间磁道。
电梯调度(125)102.94.91.86.130.147.150.175.177

4、循环扫描算法(CSCAN)
循环扫描算法是对扫描算法的改进。如果对磁道的访问请求是均匀分布的,当磁头到达磁盘的一端,并反向运动时落在磁头之后的访问请求相对较少。这是由于这些磁道刚被处理,而磁盘另一端的请求密度相当高,且这些访问请求等待的时间较长,为了解决这种情况,循环扫描算法规定磁头单向移动。例如,只自里向外移动,当磁头移到最外的被访问磁道时,磁头立即返回到最里的欲访磁道,即将最小磁道号紧接着最大磁道号构成循环,进行扫描。
循环扫描 (125)130.147.150.175.177.86.91.94.102

转自枫叶

以下是抄的代码

#include <iostream>  
#include <time.h>  
#include <vector>  
#include <math.h>  
#include <stdlib.h>  
#include <algorithm>  
#include <cstring>  
#include <windows.h>  
#include <fstream>  
using namespace std;  
  
int position = 0;      //当前磁道位置  
int dis = 0;  
double average_distance = 0;  
  
void request(vector<int>&m_vec,ofstream &outfile){  
    cout<<"随机生成磁盘序列:"<<endl;  
    int n = 0;  
    srand(time(NULL));     //添加随机数种子  
    n = rand() % 20 + 1;  
    int temp = 0;  
    for(int i=0;i<n;i++){  
        temp = rand() % 100;  
        m_vec.push_back(temp);  
        cout<<temp<<" ";  
        outfile<<temp<<endl;  
    }  
    cout<<endl;  
    position = rand() % 100;  
    cout<<"当前磁道:"<<position<<endl;  
}  
  
void compute_dis(vector<int>m_vec,int &dis,double &average_distance){  
    average_distance = (double)dis / (double)m_vec.size();  
}  
  
void FIFO(vector<int>m_vec,int position){     //先来先服务算法  
    dis = 0;  
    average_distance = 0;  
    for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){  
        dis += abs(position-*it);  
        Sleep(500);  
        cout<<"->"<<*it;  
        position = *it;  
    }  
    compute_dis(m_vec,dis,average_distance);  
}  
  
void SSTF(vector<int>m_vec,int position){   //最短寻道时间算法  
    dis = 0;  
    average_distance = 0;  
    sort(m_vec.begin(),m_vec.end());    //从小到大排序  
    int i = 0;  
    for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){  
        if(position >= *it)  
            i++;  
    }  
    int count = 0;  
    int left = i-1;  
    int right = i;  
    while(count<m_vec.size()){  
        if((left >=0 && abs(m_vec[right]-position) > abs(m_vec[left]-position)) || right>=m_vec.size()){  
            dis += abs(m_vec[left]-position);  
            Sleep(500);  
            cout<<"->"<<m_vec[left];  
            position = m_vec[left];  
            left--;  
        }  
        else{  
            dis += abs(m_vec[right]-position);  
            Sleep(500);  
            cout<<"->"<<m_vec[right];  
            position = m_vec[right];  
            right++;  
        }  
        count++;  
    }  
    compute_dis(m_vec,dis,average_distance);  
}  
  
void SCAN(vector<int>m_vec,int position){   //电梯调度算法  
    dis = 0;  
    average_distance = 0;  
    sort(m_vec.begin(),m_vec.end());    //从小到大排序  
    int i = 0;  
    for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){  
        if(position >= *it)  
            i++;      //找到position所在的磁道  
    }  
    int left = i - 1;   //先从外到内扫描  
    int right = i;  
    while(left >= 0){  
        dis += abs(position - m_vec[left]);  
        Sleep(500);  
        cout<<"->"<<m_vec[left];  
        position = m_vec[left];  
        left --;  
    }  
    while(right < m_vec.size()){  
        dis += abs(position - m_vec[right]);  
        Sleep(500);  
        cout<<"->"<<m_vec[right];  
        position = m_vec[right];  
        right ++;  
    }  
    compute_dis(m_vec,dis,average_distance);  
}  
  
void CSCAN(vector<int>m_vec,int position){   //循环扫描算法  
    dis = 0;  
    average_distance = 0;  
    sort(m_vec.begin(),m_vec.end());    //从小到大排序  
    int i = 0;  
    for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){  
        if(position >= *it)  
            i++;      //找到position所在的磁道  
    }  
    int left = i - 1;   //先从外到内扫描  
    int right = i;  
    while(left >= 0){  
        dis += abs(position - m_vec[left]);  
        Sleep(500);  
        cout<<"->"<<m_vec[left];  
        position = m_vec[left];  
        left --;  
    }  
    position = 100;     //立即到最外侧的磁道  
    int len = m_vec.size()-1;  
    while(len >= right){  
        dis += abs(position - m_vec[len]);  
        Sleep(500);  
        cout<<"->"<<m_vec[len];  
        position = m_vec[len];  
        len --;  
    }  
    compute_dis(m_vec,dis,average_distance);  
}  
  
void FSCAN(vector<int>m_vec,int position){   //分步电梯调度算法,。分两个队列  
    dis = 0;  
    average_distance = 0;  
    //SCAN(m_vec,position);  
    sort(m_vec.begin(),m_vec.end());    //从小到大排序  
    int i = 0;  
    for(vector<int>::iterator it=m_vec.begin();it!=m_vec.end();it++){  
        if(position >= *it)  
            i++;      //找到position所在的磁道  
    }  
    int left = i - 1;   //先从外到内扫描  
    int right = i;  
    while(left >= 0){  
        dis += abs(position - m_vec[left]);  
        Sleep(500);  
        cout<<"->"<<m_vec[left];  
        position = m_vec[left];  
        left --;  
    }  
    while(right < m_vec.size()){  
        dis += abs(position - m_vec[right]);  
        Sleep(500);  
        cout<<"->"<<m_vec[right];  
        position = m_vec[right];  
        right ++;  
    }  
    cout<<endl;  
    cout<<"在扫描的过程中新产生的服务序列:"<<endl;  
    vector<int>ve;  
    while(!ve.empty())  
        ve.pop_back();  
    int n = 0;  
    n = rand() % 20 + 1;  
    int temp = 0;  
    for(i=0;i<n;i++){  
        temp = rand() % 100;  
        cout<<temp<<" ";  
        ve.push_back(temp);  
    }  
    cout<<endl;  
    cout<<position;  
    SCAN(ve,position);  
    average_distance = (double)dis / (double)(m_vec.size()+ve.size());  
}  
  
void print(){  
    cout<<endl<<endl;  
    cout<<"经计算,磁头移动的总距离为:"<<dis<<endl;  
    cout<<"磁头平均移动距离:"<<average_distance<<endl;  
    cout<<endl<<endl;  
}  
  
int choose_algorithm(vector<int>m_vec){  
    cout<<endl<<endl;  
    cout<<"本实验可用的调度算法有以下5种:"<<endl;  
    cout<<"1.FIFO  2.SSTF  3.SCAN  4.CSCAN  5.FSCAN  6.结束本序列的调度  7.结束程序"<<endl;  
    int choice = 0;  
    cout<<"选择:"<<endl;  
    cin>>choice;  
    cout<<endl;  
    while(choice!=6 && choice!=7){  
        cout<<"磁盘请求的服务状况:"<<endl;  
        cout<<position;  
        switch(choice){  
            case 1:  
                FIFO(m_vec,position);break;  
            case 2:  
                SSTF(m_vec,position);break;  
            case 3:  
                SCAN(m_vec,position);break;  
            case 4:  
                CSCAN(m_vec,position);break;  
            case 5:  
                FSCAN(m_vec,position);break;  
            default:  
                cout<<"******非法输入!******"<<endl<<endl;break;   
        }   
        if(choice<=7 && choice>=1)   
            print();  
        cout<<"选择:"<<endl;  
        cin>>choice;  
    }  
    if(choice == 7)  
        return 0;  
    else  
        cout<<endl<<endl;  
    return 1;  
}  
  
int main(){  
    cout<<"---------------磁盘调度算法模拟实验-----------------"<<endl;  
    ofstream outfile;  
    outfile.open("data.txt");  
    while(1){  
        vector<int> vec;  
        while(!vec.empty())  
            vec.pop_back();  
        request(vec,outfile);         //请求服务序列   
        int flag = choose_algorithm(vec);  
        if(flag == 0)  
            break;  
    }   
    outfile.close();  
    return 0;  
}  
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,189评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,577评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,857评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,703评论 1 276
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,705评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,620评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,995评论 3 396
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,656评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,898评论 1 298
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,639评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,720评论 1 330
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,395评论 4 319
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,982评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,953评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,195评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,907评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,472评论 2 342

推荐阅读更多精彩内容

  • 一、概要 1、操作系统的内核。 2、操作系统的五大管理功能:进程管理、存储管理、...
    _Jason___阅读 997评论 0 3
  • 四、文件系统的安全性 这里我们讨论如何确保未经授权的用户不能存取某些文件? 4.1 文件保护机制 用于提供安全性、...
    yjaal阅读 1,198评论 0 1
  • 深夜的时候,青梅竹马给他打越洋电话。 “至明呀,明天我就要订婚啦。” 电话那头还是那个天真烂漫的少女。 至明低低地...
    嫣然咕噜咕噜阅读 254评论 0 1
  • 想做只猫。 安静的行走。 想动的时候,走走,不想动的时候,趴到主人的怀里,躲躲风。细软轻柔的绒毛,干干净净,晶莹剔...
    安安liyj阅读 522评论 0 3