c语言实现银行家算法

本实验是模拟和实现银行家算法。

操作系统按照银行家制定的规则为进程分配资源:

1. 当进程首次申请资源时,要测试该进程对资源的最大需求量,如果系统现存的资源可以满足它的最大需求量则按当前的申请量分配资源,否则就推迟分配。

2. 当进程在执行中继续申请资源时,先测试该进程本次申请的资源数是否超过了对该资源剩余总量。若超过则拒绝分配资源,若能满足则继续比较当前申请量与系统剩余可用量,若剩余可用量大于本次申请量则按当前的申请量尝试性分配资源,否则也要推迟分配。

3. 对本次尝试性分配进行确认:分别对所有未结束的进程进行判断,若能找到一个安全执行序列,则本次尝试性分配进行确认,否则执行回滚操作并恢复尝试性分配前的状态。

核心数据结构

int zy;//资源种类

int N,M;//N是资源数,M是进程数

int Available[MAX];//avaiable[i]表示系统中第i类资源的剩余量

int Max[MAX][MAX];//Max[i][j]表示第i个进程对第j类资源的最大需求

int Need[MAX][MAX];//need[i][j]表示第i个进程剩余所需第j类资源的数量

int Allocation[MAX][MAX];//Allocation[i][j]表示第i个进程已占有第j类资源的数量

int Finish[MAX];//finish[i]表示系统是否有能力使第i个进程执行完成

int Request[MAX][MAX];//Request[i][j]表示第i个进程某次申请第j类资源的数量

int State[MAX];//State[i]表示第i个进程所处状态(完成,进行中)

int Work[MAX];//Work[i]表示第i个类资源数量

char Name[MAX][15];//记录进程的名字

int safe_arr[MAX];

int n;//进程数

算法流程图如下:

源码 

/*
操作系统按照银行家制定的规则为进程分配资源:

1. 当进程首次申请资源时,要测试该进程对资源的最大需求量,
如果系统现存的资源可以满足它的最大需求量则按当前的申请量分配资源,否则就推迟分配。

2. 当进程在执行中继续申请资源时,先测试该进程本次申请的资源数是否超过了对该资源剩余总量。
若超过则拒绝分配资源,若能满足则继续比较当前申请量与系统剩余可用量,
若剩余可用量大于本次申请量则按当前的申请量尝试性分配资源,否则也要推迟分配。

3. 对本次尝试性分配进行确认:分别对所有未结束的进程进行判断,若能找到一个安全执行序列
,则本次尝试性分配进行确认,否则执行回滚操作并恢复尝试性分配前的状态。
*/

#include<stdio.h>
#include<string.h>
#define MAX 20
int safe();
int bank();
void show();

int N,M;//N是资源数,M是进程数
int Available[MAX];//avaiable[i]表示系统中第i类资源的剩余量
int Max[MAX][MAX];//Max[i][j]表示第i个进程对第j类资源的最大需求
int Need[MAX][MAX];//need[i][j]表示第i个进程剩余所需第j类资源的数量
int Allocation[MAX][MAX];//Allocation[i][j]表示第i个进程已占有第j类资源的数量
int Finish[MAX];//finish[i]表示系统是否有能力使第i个进程执行完成
int Request[MAX][MAX];//Request[i][j]表示第i个进程某次申请第j类资源的数量
int State[MAX];//State[i]表示第i个进程所处状态(完成,进行中)
int Work[MAX];//Work[i]表示第i类资源数量
char Name[MAX][15];//记录进程的名字
int safe_arr[MAX]; //安全队列

/*
初始化相关资源
*/
void init() {
    printf("请输入进程数量:\n");
    scanf("%d",&M);
    printf("请输入资源种类的数量:\n");
    scanf("%d",&N);
    printf("请输入%d类资源初始化的资源数:\n",N);
    for(int i=0;i<N;i++) {
        scanf("%d",&Available[i]);  //资源初始化的资源
    }
    printf("请输入进程的相关信息:\n");
    printf("进程名\t最大需求量\n");
    for(int i=0;i<M;i++) {
        scanf("%s",&Name[i]);
        for(int j=0;j<N;j++) {
            scanf("%d",&Max[i][j]);
            Need[i][j]=Max[i][j];
        }
    }
    printf("进程开始执行!\n");

    printf("请为进程分配相关资源!\n");
    bank();
    show();

}

/*
安全算法
*/
int safe() {
    
    for(int i=0;i<N;i++) {
        Work[i]=Available[i];  //初始化可工作资源Work
    }
    int i,count,num=0;
    for(i=0;i<M;i++) {  //遍历每一个进程
        count=0;
        for(int j=0;j<N;j++) {  //遍历每一个资源

            if(Finish[i]==0&&Need[i][j]<=Work[j]) {  //满足条件
                count++;
                if(count==N) {   //全满足条件,代表该进程可以执行完成
                    Finish[i]=1;

                    for(int k=0;k<N;k++) {
                        Work[k] += Allocation[i][k];   //可工作资源加上该进程以前分配的资源
                    }

                    safe_arr[num]=i;  //设置安全序列
                    num++;
                    i=-1;  // ***这里是从头开始找可以执行的进程
                }

            }
        }

    }
    for(i=0;i<M;i++) {
        if(Finish[i]==0) {
        	
        	for(int i=0;i<M;i++) {
    			Finish[i]=0;   //将Finish数组重置为0 
			}
			
            return 0;
        }
    }
    printf("申请成功!安全序列为:(可能存在多个安全序列)");
    for(i=0;i<M;i++) {
        if(State[i]==0) {
        	printf("%s",Name[safe_arr[i]]);
	        if(i<M-1) {
	            printf("->");
	        }
		}
    }
    printf("\n");
    
    for(int i=0;i<M;i++) {
    	Finish[i]=0;   //将Finish数组重置为0 
	}
    
    
    return 1;

}


/*
银行家算法
*/
int bank() {
    char name[15]; //进程的名字
	int ret = -1; //返回值

    printf("请输入进程名:\n");
    scanf("%s",name);
    int n=-1;
    while(1) { //找进程所在的编号
        for(int i=0;i<sizeof(Name)/sizeof(Name[0]);i++) {
            if(strcmp(name,Name[i])==0) {
                n=i;
            }
        }
        if(n!=-1) {
            break;
        }
        printf("请重新输入进程名:\n");
        scanf("%s",name);
    }

    
    while(1) {

        printf("请输入该进程当前申请的各个资源数量:\n");
        for(int i=0;i<N;i++) {
            scanf("%d",&Request[n][i]);
        }

        int flag=0;
        for(int i=0;i<N;i++) {
            if(Request[n][i]<=Need[n][i]&&Request[n][i]<=Available[i]) {
                flag+=1; //判断是否满足资源,统计满足资源的个数
            }
        }
        if(flag==N) {   //如果满足资源申请的条件
			
			for(int i=0;i<N;i++) {
                Available[i]-=Request[n][i];
                Need[n][i]-=Request[n][i];
                Allocation[n][i]+=Request[n][i];
            }
			
			ret = safe(); 
            if(ret) {
                int stat=0;
                for(int i=0;i<N;i++) {
                    
                    
                    if(Need[n][i]==0) {
                        stat++;
                    }
                }
                if(stat==N) {
                	
                	for(int i=0;i<N;i++) {
                		Available[i] += Allocation[n][i];  //全部满足需求就释放资源 
                		Allocation[n][i] = 0; 
					}
					
                    State[n]=1;  //更新进程状态
                }
                break;
            }else{
            	
            	for(int i=0;i<N;i++) {  //不满足就恢复 
	                Available[i]+=Request[n][i];
	                Need[n][i]+=Request[n][i];
	                Allocation[n][i]-=Request[n][i];
            	}
            	
                printf("无安全序列,请重新输入!\n");
                break;
            }


        }else {  //不满足条件
            printf("申请异常!\n");
            printf("系统可用资源如下:\n");
            for(int i=0;i<N;i++) {
                printf("%d ",Available[i]);
            }
            printf("\n当前进程剩余所需资源如下:\n");
            for(int i=0;i<N;i++) {
                printf("%d ",Need[n][i]);
            }
            printf("\n请重新输入!\n");
        }
    }
    return ret;
}



/*
打印进程信息
*/
void show() {
    
    printf("进程名\t最大需求量\t需求量\t已分配量\t执行状态\n");
    for(int i=0;i<M;i++) {
        printf("%s\t",Name[i]);
        for(int j=0;j<N;j++) {
            printf("%d ",Max[i][j]);
        }
        printf("\t\t");
        for(int j=0;j<N;j++) {
            printf("%d ",Need[i][j]);
        }
        printf("\t");
        for(int j=0;j<N;j++) {
            printf("%d ",Allocation[i][j]);
        }
        if(State[i]==0) {
            printf("\t\tWorking\n");
        }else{
            printf("\t\tFinished\n");
        }
    }
    printf("系统剩余资源:\n");
    for(int i=0;i<N;i++) {
        printf("%d ",Available[i]);
    }
    getchar();
    printf("\n");

}


int main() {
    init();
    char flag;
    while(1) {
        printf("是否需要申请资源?(Y/N):");
        scanf("%c",&flag);
        if(flag=='N'||flag=='n') {
            break;
        }
        if(flag!='N'&&flag!='Y'&&flag!='n'&&flag!='y') {
            printf("请重新输入!\n");
            continue;
        }
        int ret;
        ret = bank();
        if(ret) {
        	show();
		}

    }

    return 0;
}

程序预期运行结果截图

  • 0
    点赞
  • 51
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
操作系统银行家算法是一种资源分配和安全性管理的算法,用于确保在多进程环境中系统能够安全地分配资源。 在实验中,我们可以使用C语言实现操作系统银行家算法。首先,我们需要定义系统资源和进程的数据结构。 系统资源可以使用数组来表示,每个资源有一个初始值和可用值。例如,我们可以定义一个长度为n的资源数组available,表示系统有n个资源,available[i]表示第i个资源的可用值。另外,我们还需要定义一个长度为n的资源数组max,表示每个进程对各个资源的最大需求值。 进程也可以使用结构体来表示,包括进程的编号、各个资源的已分配值和还需值。例如,我们可以定义一个进程结构体Process,包括成员变量pid、allocation和need,其中allocation[i]表示第i个资源已分配给该进程的数量,need[i]表示第i个资源该进程还需要的数量。 在实验中,我们首先需要初始化系统资源和进程的初始值。然后,通过输入的方式获取进程对各个资源的最大需求值,同时更新每个进程的已分配值和还需值。 接下来,我们可以编写一个函数来判断系统是否处于安全状态。该函数可以对每个进程进行遍历,判断该进程是否能够满足其还需值,并且不会导致其他进程无法完成。如果所有进程都可以成功执行,则系统处于安全状态。 最后,我们可以编写一个资源分配的函数。在该函数中,首先判断分配的资源是否满足每个进程的需求,并且不会导致系统进入不安全状态。如果满足条件,则可以进行资源的分配。如果不满足条件,则需要等待或拒绝资源的分配。 通过以上的实现,我们可以模拟操作系统银行家算法的工作原理,实现资源的分配和安全性管理。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值