IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 数据结构与算法 -> 操作系统(第四版)银行家算法C++实现 -> 正文阅读

[数据结构与算法]操作系统(第四版)银行家算法C++实现

操作系统(第四版)银行家算法C++实现

仅做学习使用,只是自己的一个小练习,有些地方的代码是针对例题设置

书籍封面:
在这里插入图片描述

题目:(书籍的P111-P114页内容)

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

以下是代码(配有注释):

#include <iostream>
#include<string.h> //为了是两个数组相等memcpy函数加的头文件
using namespace std;

#define SourseNum 3  //资源种类数,例题中为ABC三种资源(书P112)
#define  N  5 //进程数,5
#define  M  3  //资源种类数
#define  A  0
#define  B  1
#define  C  2  //资源名称,在后面数组中使用的时候可以直接用名字,不需要考虑其实际值是数组下标012


//银行家算法
int Available[SourseNum]= {3,3,2}; //可利用资源数,系统拥有的
int Max[N][M]={ {7,5,3},{3,2,2},{9,0,2},{2,2,2},{4,3,3} };//最大需求矩阵
int Allocation[N][M]={ {0,1,0},{2,0,0},{3,0,2},{2,1,1},{0,0,2} }; //n进程已经拥有的m资源数量
int Need[N][M]={ {7,4,3},{1,2,2},{6,0,0},{0,1,1},{4,3,1} }; //进程n还需要m资源数量
int Request[N][SourseNum]; //存放的内容是n进程请求申请的资源数

//安全性算法
int Work[SourseNum];//工作向量,表示系统可提供给进程继续运行所需的各类资源数目,执行安全算法时Work[] = Available[]
bool Finish[N];//表示系统是否有足够的资源分配给进程使之运行完成,一开始都为false

//声明所有函数
void initial();//初始化所有资源初始值
bool banker_suanfa(int name);//银行家算法 ,name是进程序号
bool is_safe();//安全性算法
void banker_back_suanfa(int name);//不安全的时候要回退资源,银行家算法里面加减了啥都得改回去
void output();//把所有内容可视化输出,不然输着输着忘记内容了

/*
void initial(){//初始化所有资源初始值,初始化例题内容 //后续发现错误,只能在定义数组的时候整体赋值,在赋值语句中不能整体赋值。
    Available[SourseNum] = {3,3,2};
    Max[N][M]={ {7,5,3},{3,2,2},{9,0,2},{2,2,2},{4,3,3} };
    Allocation[N][M]={ {0,1,0},{2,0,0},{3,0,2},{2,1,1},{0,0,2} };
    Need[N][M]={ {7,4,3},{1,2,2},{6,0,0},{0,1,1},{4,3,1} };
}
*/
bool banker_suanfa(int name){//银行家算法,失败(当输入不合法的时候)则返回false;name是进程序号
    //(1)
    if(Request[name][A]>Need[name][A]) return false;
    if(Request[name][B]>Need[name][B]) return false;
    if(Request[name][C]>Need[name][C]) return false;
    //(2)
    if(Request[name][A]>Available[A]) return false;
    if(Request[name][B]>Available[B]) return false;
    if(Request[name][C]>Available[C]) return false;
    //(3)输入合理,进行操作
    for(int i =0 ;i<SourseNum;i++){
        Available[i]-=Request[name][i];    //系统拥有的响应资源数减少了
        Allocation[name][i] += Request[name][i]; //进程自己拥有的响应资源数增加了
        Need[name][i]-=Request[name][i]; //进程自己需要的响应资源数减少了
    }
    return true;



}
bool is_safe(){//安全性算法   //有个小问题,如果不是按照从前往后的顺序找到的序列呢?--如果work+Allocation都能本身就能把P4运行了,那先收了P2的Allocation就更能把P4运行了
    for(int k =0;k<N;k++){
        Finish[k]=false;
    }
//    Finish[N] = {false,false,false,false,false};//后续发现错误,只能在定义数组的时候整体赋值,在赋值语句中不能整体赋值。
 //   Work = Available;不能使用这种方法让两个数组相等
    memcpy(Work,Available,sizeof(Available));
    bool flag =true;  //标志位
    int i=0;
    for(;i<N;){//寻找满足条件并更新的进程
        if(Finish[i]==false && Need[i][A]<=Work[A] &&Need[i][B]<=Work[B] &&Need[i][C]<=Work[C]){
            cout<<"此时的work ABC = \t"<<Work[A]<<"\t"<<Work[B]<<"\t"<<Work[C]<<endl;
            Work[A]+=Allocation[i][A];
            Work[B]+=Allocation[i][B];
            Work[C]+=Allocation[i][C];
            Finish[i]=true;
            cout<<"安全性算法中:目前找到的进程:进程"<<i<<endl;
            cout<<"此时的work+Allocation ABC = \t"<<Work[A]<<"\t"<<Work[B]<<"\t"<<Work[C]<<endl;
            cout<<"------------------------------"<<endl;
            i=0;//从头再找一遍,就是说找到了之后,work值更新了,没准之前略过的进程又有人能行了呢。
        }
        else{
            i++;
        }
    }

    for(int j=0;j<N;j++){ //遍历查看finish值对不对
        if(Finish[j]==false){//有进程还是false说明它不合格,这个不安全
            flag=false;
            break; //直接break,别的也不用找了,找到一个不合格的这个申请就不安全了已经
        }
    }

    if(flag==false){
        return false; // 不安全!
    }else{
        return true;//安全
    }

}
void banker_back_suanfa(int name){//不安全的时候要回退资源,银行家算法里面加减了啥都得改回去

    for(int i =0 ;i<SourseNum;i++){
        Available[i]+=Request[name][i];    //系统拥有的响应资源数减少的加回去
        Allocation[name][i] -= Request[name][i]; //进程自己拥有的响应资源数增加了的减回去
        Need[name][i]+=Request[name][i]; //进程自己需要的响应资源数减少了的加回去
    }

}
void output(){//把所有内容可视化输出
    for(int i =0;i<N;i++){
        cout<<"进程P"<<i<<"的Allocation ABC:"<<Allocation[i][A]<<"\t"<<Allocation[i][B]<<"\t"<<Allocation[i][C]<<endl;
    }
    cout<<"-------------------------------------------------------"<<endl;
    for(int i =0;i<N;i++){
        cout<<"进程P"<<i<<"的Need ABC:"<<Need[i][A]<<"\t"<<Need[i][B]<<"\t"<<Need[i][C]<<endl;
    }
    cout<<"-------------------------------------------------------"<<endl;

    cout<<"Available ABC分别为:"<<Available[A]<<"\t"<<Available[B]<<"\t"<<Available[C]<<endl;

    cout<<"-------------------------------------------------------"<<endl;
    cout<<"-------------------------------------------------------"<<endl;
    cout<<"-------------------------------------------------------"<<endl;
}
bool is_End(){//是否结束,当可分配资源即Available全为0的时候,就是系统没有可分配资源的时候,结束程序
    for(int i =0;i<SourseNum;i++)
    {
        if(Available[i]>0){
            return false;//只要资源数有大于0的就代表还有资源呢,就不能结束!
        }
    }
    return true;//结束啦
}


int main()
{
    int name; //进行申请的进程序号,0——4
    int Sourse_A;//申请的A资源数量
    int Sourse_B;//申请的B资源数量
    int Sourse_C;//申请的C资源数量
 //   initial();//程序开始时初始化 //因为发现错误所以这个函数挂了
    cout<<"程序还未开始时各资源情况如下:"<<endl;
    output();//输出一遍初始化内容
    cout<<"提示:若进程申请资源成功,且是安全状态程序继续运行,若申请失败则需要重新申请"<<endl;
    while(1){
        if(is_End()) break; //如果结束了,那就结束了

        cout<<"哪个进程要申请空间?(进程0——4)"<<endl;
        cin>>name;
        cout<<"\n 分别申请ABC多少资源数(数字之间搁一个空格)?\n";
        cin>>Sourse_A>>Sourse_B>>Sourse_C;
        Request[name][A]=Sourse_A;
        Request[name][B]=Sourse_B;
        Request[name][C]=Sourse_C;

        if(banker_suanfa(name)){//输入的申请资源数合理,已分配资源给
            if(is_safe()){//如果是安全的
                cout<<"进程"<<name<<"申请资源成功,现在情况如下:"<<endl;
                output();//输出一遍所有内容
                cout<<"可以继续申请资源"<<endl;
                continue;//下一轮 while循环
            }
            else { //不安全,退回
                banker_back_suanfa(name);
                cout<<"资源申请不合理!申请资源之前的状态如下:"<<endl;
                output();
                cout<<"请重新申请资源!"<<endl;
                continue;//下一轮while循环
            }

        }
        else{//输入的申请资源数不合理,连银行家算法都过不了
            cout<<"输入的申请资源数不合理,请重新输入!现在情况如下:"<<endl;
            output();
            continue;
        }

    }//while

    cout<<"\n程序结束~!"<<endl;
    return 0;
}

以上代码能够运行,初步判断结果正确
下面是书上的例子,有兴趣的话读者可以把代码拷贝到本地运行,输入测试样例试一下。

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

over~

  数据结构与算法 最新文章
【力扣106】 从中序与后续遍历序列构造二叉
leetcode 322 零钱兑换
哈希的应用:海量数据处理
动态规划|最短Hamilton路径
华为机试_HJ41 称砝码【中等】【menset】【
【C与数据结构】——寒假提高每日练习Day1
基础算法——堆排序
2023王道数据结构线性表--单链表课后习题部
LeetCode 之 反转链表的一部分
【题解】lintcode必刷50题<有效的括号序列
上一篇文章      下一篇文章      查看所有文章
加:2021-11-10 12:39:06  更:2021-11-10 12:39:44 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2025年1日历 -2025/1/9 2:02:54-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码