实验八 磁盘管理实验

一、实验目的

  1. 通过编写和调试磁盘管理的模拟程序以加深对磁盘管理方案的理解。熟悉磁盘管理的各种调度算法
  2. 通过编写和调试模拟程序以加强对磁盘地址管理的了解。

二、实验类型
综合性实验。综合高级语言、数据结构、磁盘管理模型等多方面的知识
三、实验选题
设计一个磁盘调度管理方案。并编写模拟程序实现之。产生一个需要访问的指令地址流。它是一系列需要访问的磁盘地址。为不失一般性,你可以适当地(用人工指定地方法或用随机数产生器)生成这个序列,使得 50%的指令是顺序执行的。25%的指令均匀地散布在前地址部分,25%的地址是均匀地散布在后地址部分。

磁盘算法:FIFO、最短时间算法、单向扫描算法、双向扫描算法、电梯算法


话不多说,上代码

  • 头文件及全局变量
#include <iostream>
#include<vector>
#include <ctime>
#include <algorithm>

using namespace std;

int data[100] = {0};
int data_number = 0;
  • 比较函数
bool compare(int a, int b) {
    return a < b;    // 升序排列,如果改为return a>b ,则为降序
}
  • FCFS
int FCFS() {
    int cnt = 0;
    cout << "访问序列为:";
    for (int i = 0; i < data_number - 1; i++) {
        cout << data[i] << "  ";
        cnt += abs(data[i] - data[i + 1]);
    }
    cout << data[data_number - 1] << endl;
    cout << "总的移动次数为:" << cnt << endl;
    return cnt;
}
  • SSTF
int SSTF() {
    int tmp, m, i = 0;
    int cnt = 0;
    int done = 1;   //记录遍历的柱面个数
    cout << "访问序列为:" << data[0] << "  ";
    //遍历每一个柱面
    while (done < data_number) {
        //初始化第一个差值
        for (int j = 0; j < data_number; j++) {
            if(j != i && data[j] != -1) {
                m = j;
                tmp = abs(data[i] - data[m]);
                break;
            }
        }
        //比较其他差值
        for (int j = 0; j < data_number; j++) {
            if (j != i && data[j] != -1 && abs(data[i] - data[j]) < tmp) {
                m = j;
                tmp = abs(data[i] - data[m]);
            }
        }
        cout << data[m] << "  ";
        cnt += abs(data[i] - data[m]);
        done++;
        data[i] = -1;
        i = m;
    }
    cout << endl;
    cout << "总的移动次数为:" << cnt << endl;
    return cnt;
}
  • 单向扫描调度
int CSCAN() {    //单向扫描调度
    int tmp = data[0];
    int cnt = 0;
    sort(data, data + data_number, compare);
    int i;
    for (i = 0; i < data_number; i++) {     //for循环作用为find函数
        if (data[i] == tmp) {
            tmp = i;
            break;    // 停止循环
        }
    }
    cout << "访问序列为:" << data[tmp] << "  ";
    //第一轮单向遍历
    cnt += data[tmp];   //0到第一个柱面
    while(i < data_number - 1){   //i后面还有柱面
        cnt += data[i + 1] - data[i];
        i++;
        cout << data[i] << "  ";
    }
    if(tmp != 0) {
        cnt += data[i];   //回到0
        cnt += data[0];     //0到data[0]
        i = 0;
        cout << data[i] << "  ";
        while(i < tmp - 1){   //从data[0]到data[tmp]
            cnt += data[i + 1] - data[i];
            i++;
            cout << data[i] << "  ";
        }
    }
    cout << endl << "总的移动次数为:" << cnt << endl;
    return cnt;
}
  • 双向扫描调度
int bidirectional_scan(){   //双向扫描调度
    int tmp = data[0];
    int cnt = 0;
    sort(data, data + data_number, compare);
    int i;
    for (i = 0; i < data_number; i++) {     //for循环作用为find函数
        if (data[i] == tmp) {
            tmp = i;
            break;    // 停止循环
        }
    }
    cout << "访问序列为:" << data[tmp] << "  ";
    //第一轮单向遍历
    cnt += data[tmp];   //0到第一个柱面
    while(i < data_number - 1){   //i后面还有柱面
        cnt += data[i + 1] - data[i];
        i++;
        cout << data[i] << "  ";
    }
    if(tmp != 0) {
        cnt += data[i] - data[0];
        i = tmp - 1;
        for(; i >= 0; i--){
            cout << data[i] << "  ";
        }
    }
    cout << endl << "总的移动次数为:" << cnt << endl;
    return cnt;
}
  • 电梯调度
int SCAN(){     //电梯调度
    int choose, i, cnt = 0, tmp = data[0];
    sort(data, data + data_number, compare);
    for (i = 0; i < data_number; i++) {     //for循环作用为find函数
        if (data[i] == tmp) {
            tmp = i;
            break;    // 停止循环
        }
    }
sign:
    cout << "第一轮是向内还是向外:   1. 向内遍历    2. 向外遍历" << endl;
    cin >> choose;
    switch (choose) {
        case 1:
            for(i = tmp; i < data_number; i++){
                cout << data[i] << "  ";
            }
            cnt += data[data_number - 1] - data[tmp];
            if(tmp != 0) {
                for (i = tmp - 1; i >= 0; i--) {
                    cout << data[i] << "  ";
                }
                cnt += data[data_number - 1] - data[0];
            }
            break;
        case 2:
            for(i = tmp; i >= 0; i--){
                cout << data[i] << "  ";
            }
            cnt += data[tmp] - data[0];
            if(tmp != data_number - 1) {
                for (i = tmp + 1; i < data_number; i++) {
                    cout << data[i] << "  ";
                }
                cnt += data[data_number - 1] - data[0];
            }
            break;
        default:
            cout << "输入错误,请再输一遍。";
            goto sign;
    }
    cout << endl << "总的移动次数为:" << cnt << endl;
    return cnt;
}
  • 菜单
void menu() {
    cout << endl;
    cout << "************************************************************************" << endl;
    cout << "                                 磁盘管理算法                      " << endl;
    input();
    cout << "             1. FCFS              2. SSTF             3. 单向扫描调度      " << endl;
    cout << "             4. 双向扫描调度        5. 电梯调度           6. 退出程序          " << endl;
    int choose;
    recin:
    cin >> choose;
    switch (choose) {
        case 1:
            FCFS();
            break;
        case 2:
            SSTF();
            break;
        case 3:
            CSCAN();
            break;
        case 4:
            bidirectional_scan();
            break;
        case 5:
            SCAN();
            break;
        case 6:
            cout << "程序正常结束,欢迎再次使用。";
            exit(-1);
        default:
            cout << "输入错误,请重新输入。" << endl;
            goto recin;
    }
}
  • 数据获取
  1. 手动输入
  2. 随机生成
  3. 文件获取
void input() {
    int choose;
    int number_of_Cylinders;    //只有1和2情况有用到此变量
    cout << "请选择输入数据的方式:    1. 手动输入    2. 随机生成    3. 文件读取" << endl;
    cin >> choose;
    switch (choose) {
        case 1:
            cout << "请输入柱面数目:";
            cin >> number_of_Cylinders;
            cout << "请输入柱面号的数目:";
            cin >> data_number;
            cout << "请依次输入柱面号:";
            for (int i = 0; i < data_number; i++) {
                cin >> data[i];
                if (data[i] >= number_of_Cylinders) {
                    cout << "柱面号超出范围,请重新输入。" << endl;
                    i--;
                }
            }
            break;
        case 2:
            cout << "请输入柱面数目:";
            cin >> number_of_Cylinders;
            cout << "请输入柱面号的数目:";
            cin >> data_number;
            srand((int) time(0));  // 产生随机种子  把0换成NULL也行
            for (int i = 0; i < data_number; i++) {
                data[i] = rand() % number_of_Cylinders;
            }
            break;
        case 3:
            read_file();
            break;

    }
    cout << "输入的序列为:";
    for (int i = 0; i < data_number; i++) {
        cout << "  " << data[i];
    }
    cout << endl;
}
  • 文件读取
void read_file() {
    FILE *fp = fopen("C:\\Users\\Louisthecat\\Desktop\\project\\CLion_files\\exp7\\data.txt", "r");
    if (fp == NULL) {
        printf("文件读取无效。\n");
        return;
    }
    int i;
    for (i = 0; !feof(fp); i++)
        fscanf(fp, "%d", &data[i]);
    data_number = i;
    cout << endl;
}
  • main
int main() {
    while (true)
        menu();
}
  • data.txt内容如下

53 98 183 37 122 14 124 65 67

部分演示
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

  • 6
    点赞
  • 26
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Caseythekiwi_

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值