银行家算法

一 银行家算法简介

     避免死锁

二 代码实现

package How_2;

import java.awt.DisplayMode;
import java.util.Arrays;
import java.util.LinkedList;
import java.util.Scanner;

import javax.imageio.stream.MemoryCacheImageInputStream;

import org.omg.CORBA.Request;

class resource   //资源类
{
    int []v;
    int []m;    // 当前剩余资源数组
    public resource(int[] v,int []m)
    {
        this.v=v;
       	this.m=m;  	
    }
}
class process   //进程类
{
    static resource myResource;
    int id;               //进程标识
    int []max;            //最大需求量
    int []allocation;     //已分配量
    int []need;           //剩余需求量
    public process(resource myResource,int []max,int []allocation,int id)
    {
        this.myResource=myResource;	
        this.max=max;
        this.allocation=allocation;
        this.need=new int[max.length];
        this.id=id;
        for(int i=0; i<this.need.length; i++)
        {
            this.need[i]=this.max[i]-allocation[i];
        }
    }
}
class banker     //设置银行家
{
   int  []Request;
   LinkedList<process> Process;
   int p;
   process thisprocess;
   String safeQueue="";                     //安全序列
   public banker(LinkedList myProcess)      //类资源
   {
       this.Process=myProcess;
       
   }
   public void request(int p,int []Request)      //资源请求
   {
       this.Request=Request;
       thisprocess=(process)Process.get(p);
       //判断请求合理性
       this.p=p;
       if(cheekM()&&cheekNeed())
       {
           //假设可以分配
           //更新m向量
           //不足:对矩阵运算符的重载
           for(int i=0; i<thisprocess.myResource.m.length; i++)
           {
               thisprocess.myResource.m[i]-=Request[i];
               thisprocess.need[i]-=Request[i];
               thisprocess.allocation[i]+=Request[i];
//			   System.out.println("77777777777777");
//			   System.out.println("thisprocess.myResource.m["+i+"]"+thisprocess.myResource.m[i]);
           }
           if(cheekSafe())
           {
               System.out.println("请求成功!");
               System.out.println("安全序列为:");
               System.out.println(safeQueue);
               safeQueue="";
               //更新状态
               //更改need
               //更改allocation
           }
           else  //不安全,拒绝分配
           {
               System.out.println("此状态不安全,无法分配!!!");
               for(int i=0; i<thisprocess.myResource.m.length; i++) //恢复资源状态
               {
                   thisprocess.myResource.m[i]+=Request[i];
                   thisprocess.need[i]+=Request[i];
                   thisprocess.allocation[i]-=Request[i];
               }
           }
       }
       display();
   }
   public  boolean cheekM()   					//检查当前资源是否满足要求,充足
   {
       boolean agree=true;
//	   System.out.println("5555555555555555");
       for(int i=0; i<thisprocess.myResource.m.length; i++)
       {
           if(Request[i]>thisprocess.myResource.m[i])  //请求不合理
           {
               agree=false;
               System.out.println("资源不足,拒绝请求!!!");
               break;
           }
//		   System.out.println("Request["+i+"]="+Request[i]);
//		   System.out.println(""+thisprocess.myResource.m[i]);
       }
       return agree;
   }
   public  boolean cheekNeed()   //检查请求是否合理
   {
       boolean agree=true;
       for(int i=0; i<thisprocess.need.length; i++)
       {
           if(Request[i]>thisprocess.need[i])  //请求不合理
           {
               agree=false;
               System.out.println("请求非法!!!");
               break;
           }
//		   System.out.println("66666666666666666666666666");
           System.out.println("Request["+i+"]="+Request[i]);
           System.out.println(""+thisprocess.need[i]);
       }
       return agree;
   }
   public  boolean cheekSafe()    //检查安全状态   核心代码
   {
       boolean agree=false;
       int []temp_m=new int [thisprocess.myResource.m.length];
       //System.out.println("复制数组");
       //复制数组
       temp_m=Arrays.copyOf(thisprocess.myResource.m, thisprocess.myResource.m.length);
       
       //复制链表    形成动态数组,这是银行家算法的关键
       //结束条件    数组变空   状态安全
       //结束条件    类似冒泡算法    只要有一次比较完temp_process的所以元素儿没有比m向量小的,此状态不安全
       //安全判断    v=m   资源可以全部收回
       
       LinkedList<process> temp_process=new LinkedList<process>();
       for(int i=0; i<Process.size(); i++)
       {
           temp_process.add(Process.get(i));
       }
//	   System.out.println("进程"+1+":");
//	   process itProcess=temp_process.get(1);
//	   System.out.println("max[i]");
//	   for(int ele:itProcess.max)
//	   {
//		   System.out.print(ele+"	");
//	   }
       
//	   System.out.println();;
//	   for(int ele:temp_m)
//	   {
//		  System.out.print(""+ele+"	");
//	   }
//	   System.out.println();
       boolean count=true;
       do 
       {
           int i=0;
           count=false;
           for(i=0; i<temp_process.size(); i++)
           {
//			   System.out.println("+++++++++++++++++++++++++++");
               boolean yes=true;     //比较need
               process itProcess1=(process) temp_process.get(i);
//			   System.out.println("进程"+itProcess1.id);
               //探查need矩阵
               for(int j=0; j<temp_m.length; j++)
               {
                   
                   if(itProcess1.need[j]>temp_m[j])
                   {
                       yes=false;
//					   System.out.println("break");
                       break;
                   }
//				   System.out.println("itProcess.need["+j+"]"+itProcess1.need[j]);
//				   System.out.println("temp_m["+j+"]"+temp_m[j]);
               }
//			   System.out.println("max[i]");
//			   for(int ele:itProcess1.max)
//			   {
//				   System.out.print(ele+"	");
//			   }
//			   System.out.println();
//			   System.out.println("+++++++++++++++++++++++++++");
               if(yes)  //need矩阵探查满足,开始回收此进程的allocation矩阵
               { 
//				   System.out.println("kkkkkkkkkkkkkkkkkkkkkkk");
                   for(int k=0; k<temp_m.length; k++)
                   {
                       temp_m[k]+=itProcess1.allocation[k];  //收回分配
                   }
//				   for(int ele:temp_m)
//				   {
//					  System.out.print(""+ele+"	");
//				   }
                   safeQueue+=""+temp_process.get(i).id;
                   count=true;
                   temp_process.remove(i); 
                   i=-1;
// for循环重头开始           令i=-1 而不是让i=0
// 否则会导致资源无法遍历  进程1				   
               }
           }
       } 
       while(count&&!temp_process.isEmpty());                    //存在安全状态等价条件
//	   if(Arrays.equals(temp_m, thisprocess.myResource.v))       //分配全部收回
//	        数组相等
       if(count) 
       {
           agree=true;
       }
       return agree;
   }
   public void display()
   {
       System.out.println("m[i]:");
       for(int ele:thisprocess.myResource.m)
       {
           System.out.print(ele+"	");
       }
       System.out.println();
       for(int i=0; i<Process.size(); i++)
       {
         
           process itProcess=Process.get(i);
           System.out.println("进程"+itProcess.id+":");
           System.out.println("max[i]");
           for(int ele:itProcess.max)
           {
               System.out.print(ele+"	");
           }
           System.out.println();
           System.out.println("allocation[i]");
           for(int ele:itProcess.allocation)
           {
               System.out.print(ele+"	");
           }
           System.out.println();
           System.out.println("need[i]");
           for(int ele:itProcess.need)
           {
               System.out.print(ele+"	");
           }
           System.out.println(); 
       }
   }
}
public class bin_1 
{
    public static void main(String[] args) 
    {
        int v[]={10,5,7};    //总的资源数
        int m[]={3,2,2};     //剩余资源
        resource myResource=new resource(v,m);
        LinkedList<process> myProcesses=new LinkedList<process>();
        
        int max0[]={7,5,3};          //最大需求举证
        int allocation0[]={0,1,0};   //已分配资源
        process process0=new process(myResource, max0, allocation0,1);
        myProcesses.add(process0);
        
        int max1[]={3,2,2};
        int allocation1[]={2,1,0};
        process process1=new process(myResource, max1, allocation1,2);
        myProcesses.add(process1);
        
        int max2[]={9,0,2};
        int allocation2[]={3,0,2};
        process process2=new process(myResource, max2, allocation2,3);
        myProcesses.add(process2);
        
        int max3[]={2,2,2};
        int allocation3[]={2,1,1};
        process process3=new process(myResource, max3, allocation3,4);
        myProcesses.add(process3);
        
        int max4[]={4,3,3};
        int allocation4[]={0,0,2};
        process process4=new process(myResource, max4, allocation4,5);
        myProcesses.add(process4);
        
        
        
        banker myBanker=new banker(myProcesses);
        myBanker.display();
        
        Scanner how=new Scanner(System.in);
        int []zero={0,0,0};
        while(true)
        {
            int []myRequest=new int[m.length];
            int p;
            System.out.println("请输入请求进程:");
            p=how.nextInt();
            p--;   //下标从0开始
            System.out.println("请输入请求资源:");
            for(int i=0; i<myRequest.length; i++)
            {
            	myRequest[i]=how.nextInt();
            }
            myBanker.request(p, myRequest);
        }
    }
}


三 运行结果

m[i]:
3	2	2	
进程1:
max[i]
7	5	3	
allocation[i]
0	1	0	
need[i]
7	4	3	
进程2:
max[i]
3	2	2	
allocation[i]
2	1	0	
need[i]
1	1	2	
进程3:
max[i]
9	0	2	
allocation[i]
3	0	2	
need[i]
6	0	0	
进程4:
max[i]
2	2	2	
allocation[i]
2	1	1	
need[i]
0	1	1	
进程5:
max[i]
4	3	3	
allocation[i]
0	0	2	
need[i]
4	3	1	
请输入请求进程:
2
请输入请求资源:
1
0
2
Request[0]=1
1
Request[1]=0
1
Request[2]=2
2
请求成功!
安全序列为:
24135
m[i]:
2	2	0	
进程1:
max[i]
7	5	3	
allocation[i]
0	1	0	
need[i]
7	4	3	
进程2:
max[i]
3	2	2	
allocation[i]
3	1	2	
need[i]
0	1	0	
进程3:
max[i]
9	0	2	
allocation[i]
3	0	2	
need[i]
6	0	0	
进程4:
max[i]
2	2	2	
allocation[i]
2	1	1	
need[i]
0	1	1	
进程5:
max[i]
4	3	3	
allocation[i]
0	0	2	
need[i]
4	3	1	
请输入请求进程:

四 总结收获

 1. 程序架构    
 class resource  //资源类
 class process   //进程类
 class banker     //设置银行家
 逐渐走入面向对象编程的方向
2.  核心代码  使用过了Linkledist
3.  核心代码 模仿改进版的冒泡排序

五 不足
.

	 矩阵运算都使用for循环,应当考虑重载
	 其次应该改进进程类的数据结构,使其拥有
	 更强的健壮性
	 可以考虑做gui界面
原文地址:https://www.cnblogs.com/Howbin/p/9941975.html