#include<stdio.h>
#include <string.h>
#include <stdlib.h>
#define MaxNumber 20
static int n;//当前进程个数
static int m;//当前资源个数
static int Available[MaxNumber];
static int Max[MaxNumber][MaxNumber];
static int Allocation[MaxNumber][MaxNumber];
static int Need[MaxNumber][MaxNumber];
static int Request[MaxNumber];
static int SafeOrder[MaxNumber];
static bool Finish[MaxNumber];
void input();//输入
bool isSystemSafe();//安全性算法
void bankerAlgorithm();//银行家算法
int main()
{
input();
if(isSystemSafe()) //先判断输入的数据有没有安全序列;
bankerAlgorithm();
else
printf("\n输入的资源分配表不存在安全序列!\n");
return 0;
}
void bankerAlgorithm() //银行家算法
{
int chooseProcess;
char isContinue;
int s=0; //分配次数
while(true)
{
//设置两个布尔变量:判别请求向量是等待还是系统已经不再分配新的资源
bool isRequestNeedOK = true;
bool isRequestAvailableOK = true;
int isAll_0=1;
int isSafe=1;
char sure;
if(s==0)
{
printf("\n请输入要申请资源的进程号(注意:P0进程为0):\n");
scanf("%d",&chooseProcess);
printf("请输入进程所请求的各类资源的数量:\n");
s=1;
}
else
{
printf("是否再次请求分配? 是请按 Y/y , 否请按 N/n :\n");
scanf("%s",&sure);
if(sure=='Y' || sure =='y')
{
printf("\n请输入要申请资源的进程号(注意:P0进程为0):\n");
scanf("%d",&chooseProcess);
printf("请输入进程所请求的各类资源的数量:\n");
}
if(sure=='N' || sure =='n')
break;
}
for(int i=0;i<m;i++)
scanf("%d",&Request[i]);
//输入错误判断
for (int i=0;i<m;i++)
{
if (Request[i]>Need[chooseProcess][i])
{
printf("\n您输入的请求进程所对应的资源数量超过最大需求量,请重新输入!\n");
isRequestNeedOK = false;
break;
}
if (Request[i]>Available[i])
{
printf("\n您输入的请求进程的资源数量超过系统所供给的最大资源数量,必须等待。请重新输入!\n");
isRequestAvailableOK = false;
break;
}
}
if(isRequestNeedOK && isRequestAvailableOK) //当输入满足最基本的要求(上面两条)
{
for (int j = 0;j<m;j++)
{
Available[j] -= Request[j];
Allocation[chooseProcess][j] += Request[j];
Need[chooseProcess][j] -= Request[j];
}
printf("\n-----同意分配请求----------");
if (!isSystemSafe()) //如何不满足系统安全性算法,将本次试探作废,恢复到原来的值
{
isSafe=0;
for (int j = 0;j<m;j++)
{
Available[j] +=Request[j];
Allocation[chooseProcess][j] -= Request[j];
Need[chooseProcess][j] += Request[j];
}
printf("\n---系统将进入不安全状态,故不分配资源---\n");//系统将进入不安全状态,故不分配资源
}
//资源回收
for(int j=0;j<m;j++)
{
if(Need[chooseProcess][j]!=0)
{
isAll_0=0; //说明不是全0,即进程还未满足
break;
}
}
if(isAll_0==1)
{
for(int j=0;j<m;j++)
Available[j] += Allocation[chooseProcess][j];
}
}
}
}
bool isSystemSafe() //安全性算法
{
int work[MaxNumber];
for (int i=0;i<m;i++) //m是资源个数A,B,C
work[i] = Available[i];
for (int i=0;i<n;i++) //n是进程个数
{
Finish[i] = false;
SafeOrder[i] = -1; //初始化, 安全序列
}
int FinishNumber = 0; //安全序列下标
int isSafe; //能分配执行安全算法的进程个数
int i =0,j;
while(i<n)
{
isSafe = 0;
for(j = 0;j<m;j++) //找到 work 满足的 need 进程
{
if (Finish[i]==false && Need[i][j]<=work[j])
isSafe++;
else
break;
}
if (isSafe == m) //当且仅当进程对应的所有资源的数量都满足的时候才成立
{
Finish[i] = true;
SafeOrder[FinishNumber] = i; //记录 安全序列 的进程号
FinishNumber++;
for (j = 0;j<m;j++)
work[j] += Allocation[i][j]; //更新 work 的资源
i=0; //找到满足条件的进程后,从头开始再进行寻找
}
else
i++; //开始下一个进程 查询
if (FinishNumber==n)
{
printf("\n-----系统是安全的----------");
printf("\n-----系统的安全序列为:-----\n");
for(int i=0;i<n-1;i++)
printf("P%d--->",SafeOrder[i]);
printf("P%d\n",SafeOrder[n-1]);
return true;
}
}
return false;
}
void input()
{
printf("请输入进程的数目:\n");
scanf("%d",&n);//当前进程个数
printf("请输入资源的数目:\n");
scanf("%d",&m);//当前资源个数
printf("请输入每个进程的 Max 资源的数目:\n");
for (int i=0;i<n;i++)
for (int j=0;j<m;j++)
scanf("%d",&Max[i][j]);
printf("请输入每个进程的 Allocation 资源的数目:\n");
for (int i=0;i<n;i++)
for (int j=0;j<m;j++)
scanf("%d",&Allocation[i][j]);
printf("请输入各个资源现有的数目:\n");
for (int i=0;i<m;i++)
scanf("%d",&Available[i]);
for (int i=0;i<n;i++) //给 Need 数组赋值
for (int j=0;j<m;j++)
Need[i][j]=Max[i][j]-Allocation[i][j];
}
07-16