admin 管理员组

文章数量: 887021

银行家算法是避免死锁的一种重要方法,能够有效的在资源分配的过程中,对系统的安全性进行检测。

通过银行家算法设计与实现,可以加深对死锁的理解,掌握死锁的预防、避免、检测和解除的基本原理,重点掌握死锁的避免方法—银行家算法。初步具有研究、设计、编制和调试操作系统模块的能力。

实验

1.有录入界面,动态录入进程个数、资源种类数、诸进程对各类资源的最大需求、T0时刻系统为诸进程分配的资源数以及系统中各类资源的资源总数;

2.能够判断T0时刻系统是否安全,进程之间能否无死锁的运行下去,若能输出安全序列。

3.有输出界面,能够从录入界面模拟进程又提出新的申请,根据银行家算法判断请求是否能得到满足,并输出当前时刻下诸进程对各类资源的需求列表及系统可用资源数,若能输出安全序列,若不能分配输出无法分配的原因;

对整个程序的大致流程(见图一),输入资源种类数、进程数以及每个种类的最大资源数,对每个进程输入它的Max、Allocation等数据。利用银行家算法输出T0时刻的状态,然后对进程添加新的请求资源,利用安全性算法检验其安全性,然后输出此时的状态。

 

 

输出其初始化后的表格

 

 

使用安全性算法对T0时刻的资源分配情况进行分析,并输出其安全性序列:

该算法需要设置两个向量,工作向量Work,它表示系统可提供给进程继续运行所需要的各类资源数目,在开始执行时,Work = Available;Finish,它表示系统是否有足够的资源分配给进程,使之运行完成。开始先做Finish[i] = false;当有足够资源分配给进程时,再另Finish[i] = true。从进程集合中找到一个满足两个条件的基础1.Finish[i] = false;2.Need[i,j] <= Work[j];若找到则改变Work和Finish的量,然后继续上一步。如果所有进程的Finish = true都满足,则系统是安全的,否则是不安全的。

安全性算法流程图

 

 

运行结果如下

 

 

分配一个请求资源p1,发出请求向量Request

 

 

采用银行家算法对资源分配情况进行分析,对请求进程进行其Request与Need和Available进行比较,并尝试分配资源。 

银行家算法流程图

 

源码如下

public class Main {

    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        boolean Choose = true;
        String C;
        System.out.println("请输入进程个数:");
        int count = in.nextInt();
        System.out.println("请输入资源种类数:");
        int number = in.nextInt();
        BankerAlgorithm T = new BankerAlgorithm(count,number);
        T.start(count,number);
        while (Choose) {
            T.setRequest(count,number);
            System.out.println("您是否还要进行资源请求:y/n?");
            C = in.next();
            if (C.equals("n")) {
                Choose = false;
            }
            if(C.equals("y")){
                Choose = true;
            }
        }
    }
}

 

public class BankerAlgorithm {

    int[] Available; // 系统可用资源
    int[][] Max; // 进程需要资源的最大数目
    int[][] Allocation; //进程当前已经获得资源的数目
    int[][] need;       //进程尚需的资源数
    int[][] Request;     //存放请求
    int[] Work;         //试分配
    int[] tmp;         //进程执行顺序
    int num = 0; //进程编号


    Scanner sc = new Scanner(System.in);

    //含参构造函数,proc是进程数形参,sour是资源种类数形参
    public BankerAlgorithm(int proc,int sour) {
        Available = new int[sour];
        Max = new int[proc][sour];
        Allocation = new int[proc][sour];
        need = new int[proc][sour];
        Request = new int[proc][sour];
        Work = new int[sour];
        tmp = new int[proc];
    }

    //设置各初始系统变量,并判断是否处于安全状态
    public void start(int proc,int sour) {
        setAvailable(sour);
        setMax(proc,sour);
        setAllocation(proc,sour);
        printSystemVariable(proc,sour); //打印矩阵
        securityAlgorithm(proc,sour);
    }

    //设置Available数组
    public void setAvailable(int sour){
        System.out.println("请设置各资源总数:");
        for (int i=0; i<sour; i++) {
            Available[i] = sc.nextInt();
        }
    }

    //设置Max矩阵
    public void setMax(int proc, int sour) {
        System.out.println("请设置各进程的最大需求矩阵:");
        System.out.println("请输入各进程的最大资源需求量");
        for (int i = 0; i < proc; i++) {
            for (int j = 0; j < sour; j++) {
                Max[i][j] = sc.nextInt();
            }
        }
    }

    //设置已分配资源矩阵Allocation
    public void setAllocation(int proc, int sour) {
        System.out.println("请设置各进程分配矩阵Alloction:");
        System.out.println("请输入各进程的已分配资源量:");
        for (int i = 0; i < proc; i++) {
            for (int j = 0; j < sour; j++) {
                Allocation[i][j] = sc.nextInt();
            }
        }

        //修改这两个变量中的值
        System.out.println("Available = Available - Allocation.");
        System.out.println("Need = Max - Allocation.");

        //设置Allocation矩阵
        for (int i = 0; i < sour; i++) {
            for (int j = 0; j < proc; j++) {
                Available[i] = Available[i] - Allocation[j][i];
            }
        }

        //设置need矩阵
        for (int i = 0; i < proc; i++) {
            for (int j = 0; j < sour; j++) {
                need[i][j] = Max[i][j] - Allocation[i][j];
            }
        }
    }

    //打印矩阵
    public void printSystemVariable(int proc, int sour) {
        System.out.println("此时资源分配量如下:");
        System.out.println("进程  "+"   Max   "+"   Alloction "+"    Need  "+"     Available ");
        for (int i = 0; i < proc; i++) {
            System.out.print("P"+i+" ");
            for (int j = 0; j < sour; j++) {
                System.out.print(Max[i][j]+" ");
            }
            System.out.println("| ");
            for (int j = 0; j < sour; j++) {
                System.out.print(Allocation[i][j]+" ");
            }
            System.out.println("+ ");
            for (int j = 0; j < sour; j++) {
                System.out.print(need[i][j] + " ");
            }
            System.out.println("+ ");
            if (i == 0) {
                for (int j = 0; j < sour; j++) {
                    System.out.println(Available[j]+" ");
                }
            }
            System.out.println();
        }
    }

    //设置请求资源量
    public void setRequest(int proc, int sour) {
        System.out.println("请输入请求资源的进程编号:");
        num = sc.nextInt();//设置全局变量进程编号num,在开头
        System.out.println("请输入请求各资源的数量:");

        for (int i = 0; i < sour; i++) {
            Request[num][i] = sc.nextInt();
        }

        String str = Arrays.toString(Request[num]);
        System.out.println("即进程P" + num + "对各资源请求Request:(" +
                str+")");
        BankerAlgorithmReal(proc,sour);
    }

    //银行家算法
    public void BankerAlgorithmReal(int proc, int sour) {
        //定义布尔类型变量,如果银行家算法执行成功即true,就进行安全检查
        boolean T = true;
        int count = 0;
        int number = 0;

        //判断request是否小于need
        for (int i = 0; i < sour; i++) {
            if (Request[num][i] <= need[num][i]) {
                count++;
            }
        }

        //判断request是否小于available
        for (int i = 0; i < sour; i++) {
            if (Request[num][i] <= Available[i]) {
                number++;
            }
        }

        //执行第二步,改变数据
        if (count == sour) {
            if (number == sour) {
                for (int i = 0; i < sour; i++) {
                    Available[i] -= Request[num][i];
                    Allocation[num][i] += Request[num][i];
                    need[num][i] -= Request[num][i];
                }
            }else {
                System.out.println("当前系统没有多余资源可分配,请等待");
                T = false;
            }
        }else {
            System.out.println("进程P"+num+"请求的资源量已经超过最大需求量need");
            T = false;
        }

        //现在是T == true了,要执行安全算法
        int b = 0;
        if (T) {
            printSystemVariable(proc,sour);
            System.out.println("现在进入安全算法");
            boolean Q = securityAlgorithm(proc,sour);
            if(!Q) {
                System.out.println("进程" + num + "申请资源后,系统进入死锁状态,分配失败!");
                for (int i = 0; i < sour; i++) {
                    Available[i] += Request[num][i];
                    Allocation[num][i] -= Request[num][i];
                    need[num][i] += Request[num][i];
                }
            }else {
                for (int i = 0; i < sour; i++) {
                    if (need[num][i] == 0) {  //说明已经不需要分配了
                        b++;
                    }
                }
                if(b == sour) {
                    for (int i = 0; i < sour; i++) {
                        Available[i] += Allocation[num][i];
                    }
                    printSystemVariable(proc, sour);
                }
            }

        }

    }

    //安全性算法
    public boolean securityAlgorithm(int proc, int sour) {
        //初始化finish
        boolean[] finish = new boolean[proc];
        for (int i = 0; i < proc; i++) {
            finish[i] = false;
        }
        boolean lable = false;
        int apply; // 计数标志
        int circle = 0;
        int count = 0; // 完成进程数

        if (sour >= 0) System.arraycopy(Available, 0, Work, 0, sour);

        boolean flag = true;

        while(count < proc) {
            if (flag) {
                System.out.println("进程  " + "   Work  " + "   Alloction " + "    Need  " + "     Work+Alloction "+"  Finish");
                flag = false;
            }

            //遍历进程
            for (int i = 0; i < proc; i++) {
                apply = 0;
                for (int n = 0; n < sour; n++) {
                    //判断进程是否已分配成功
                    if (!finish[i] && need[i][n] <= Work[n]) {
                        // 若没有分配,且资源需求数小于可用资源数,输出
                        apply++;
                        if (apply == sour) {
                            System.out.print("P" + i + "  ");

                            for (int m = 0; m < sour; m++) {
                                System.out.print(Work[m] + "  ");
                            }

                            System.out.print("|  ");

                            for (int j = 0; j < sour; j++) {
                                Work[j] += Allocation[i][j];
                            }

                            finish[i] = true;//当前进程能满足时,设为true
                            tmp[count] = i;
                            count++;//满足,进程数加1

                            for (int j = 0; j < sour; j++) {
                                System.out.print(Allocation[i][j] + "  ");
                            }

                            System.out.print("|  ");

                            for (int j = 0; j < sour; j++) {
                                System.out.print(need[i][j] + "  ");
                            }

                            System.out.print("|  ");

                            for (int j = 0; j < sour; j++) {
                                System.out.print(Work[j] + "  ");
                            }

                            System.out.print("\t" + " |  ");


                            System.out.print("\t" + finish[i]);

                            System.out.println();
                        }

                    }
                }
            }
            circle++;

            if (count == proc) {
                lable = true;
                System.out.println("系统是安全的");
                System.out.print("此时存在一个安全序列:");
                for (int i = 0; i < proc; i++) {
                    System.out.print("P" + tmp[i]);
                    if (i < proc - 1) {
                        System.out.print("->");
                    }
                }
                System.out.println();
                break;
            }
            if (count < circle) {
                count = proc;
                lable = false;
                for (int i = 0; i < proc; i++) {
                    if (!finish[i]) {
                        System.out.println("当前系统处于不安全状态,故不存在安全序列");
                        break;
                    }
                }
            }
        }
        return lable;
    }
}


 

本文标签: 银行家 算法 操作系统