银行家算法的实现_操作系统实验报告利用银行家算法避免死锁

  计算机操作系统实验报告

 题 目 利用银行家算法避免死锁

 一、 实验目的:

 1、 加深了解有关资源申请、避免死锁等概念,并体会和了解死锁和避免死 锁的具体实施方法。

 2、 要求编写和调试一个系统动态分配资源的简单模拟程序,观察死锁产生 的条件,并采用银行家算法,有效的防止和避免死锁的发生。

 二、 实验内容:

 用银行家算法实现资源分配:

 设计五个进程{p0,p1,p2,p3,p4}共享三类资源{A,B,C}的系统,例如, {A,B,C}的资源数量分别为10,5,7。进程可动态地申请资源和释放资源, 系统按进程的申请动态地分配资源, 要求程序具有显示和打印各进程的某一 个时刻的资源分配表和安全序列; 显示和打印各进程依次要求申请的资源号

 以及为某进程分配资源后的有关资源数据。

 三、 问题分析与设计:

 1、 算法思路:

 先对用户提出的请求进行合法性检查,即检查请求是否大于需要的,是 否大于可利用的。若请求合法,则进行预分配,对分配后的状态调用安全性 算法进行检查。若安全,则分配;若不安全,则拒绝申请,恢复到原来的状 态,拒绝申请。

 2、 银行家算法步骤:

 如果Request v or二Need,则转向步骤 ⑵;否则,认为出错,因 为它所需要的资源数已超过它所宣布的最大值。

  如果Requestv or二Available,则转向步骤(3);否则,表示系统中 尚无足够的资源,进程必须等待。

 系统试探把要求的资源分配给进程 Pi, 并修改下面数据结构中的数 值:

 Available=Available-Request[i];

 Allocation=Allocation+Request;

 Need=Need-Request;

 系统执行安全性算法,检查此次资源分配后,系统是否处于安全状 态。

 3、安全性算法步骤:

 ( 1 )设置两个向量

 工作向量Work。它表示系统可提供进程继续运行所需要的各类资源数 目,执行安全算法开始时, Work=Allocation;

 布尔向量 Finish 。它表示系统是否有足够的资源分配给进程, 使之运 行完成,开始时先做 Finish[i]=false ,当有足够资源分配给进程时,令 Finish[i]=true 。

 (2)从进程集合中找到一个能满足下述条件的进程:

 Fi nish[i]=false

 Needvor二Work

 如找到,执行步骤( 3);否则,执行步骤( 4)。

 ( 3)当进程 P 获得资源后,可顺利执行,直至完成,并释放出分配给它的资源,故应执行:

 Work=Work+Allocation;

 Finish[i]=true;

 转向步骤( 2)。

 否则,系( 4)如果所有进程的 Finish[i]=true, 则表示系统处于安全状态; 统处于不安全状态。

 否则,系

 4、流程图:

 系统主要过程流程图

 银行家算法流程图

 安全性算法流程图

 5、主要数据结构

 假设有M个进程N类资源,则有如下数据结构:

 int max[M*N] M 个进程对N类资源的最大需求量

 int available[N] 系统可用资源数

 int allocated[M*N] M 个进程已经得到N类资源的资源量

 int need[M*N] M 个进程还需要N类资源的资源量

 int worked[] 系统提供给进程继续运行所需的各类资源数目

 四、 源代码

 import .*;

 import .*;

 import .*;

 public class OsBanker extends JFrame { etBounds(0, 0 + pi * 20, 60,

 20);

 labelProcessLabel2[pi].setBounds(0, 0 + pi * 20, 60, 20);

 }

 (75, 120, 60, 120);

 (75, 270, 60, 120);

 for (int pi = 0; pi < 6; pi++) {

 (labelProcessLabel1[pi], null);

 (labelProcessLabel2[pi], null);

 }

 (pPanel1);

 (pPanel2);

 (pPanel4);

 for (int si = 0; si < 5; si++)

 for (int pi = 0; pi < 6; pi++) {

 textNeed[pi][si] = new JTextField();

 textNeed[pi][si]

 .setBounds(150 + si * 50, 120 + pi * 20, 50, 20); textNeed[pi][si].setEditable(false);

 textAllocation[pi][si] = new JTextField(); textAllocation[pi][si].setBounds(150 + si * 50, 270 +

 pi * 20,

 50, 20);

 }

 }

 textAllocation[pi][si].setEditable(false);

 for (int si = 0; si < 5; si++) {

 textAvailable[si] = new JTextField();

 textAvailable[si].setEditable(false);

 textAvailable[si].setBounds(150 + si * 50, 70, 50, 20); textRequest[si] = new JTextField();

 textRequest[si].setEditable(false);

 textRequest[si].setBounds(150 + si * 50, 430, 50, 20); (textAvailable[si], null);

 (textRequest[si], null);

 }

 for (int pi = 0; pi < 6; pi++)

 for (int si = 0; si < 5; si++) {

 (textNeed[pi][si], null);

 (textAllocation[pi][si], null);

 }

 (80, 430, 50, 20);

 (textProcessName, null);

 (550, 500);

 (false);

 (" 银行家算法 (SXJ)");

 (null);

 (EXIT_ON_CLOSE); dd(scrollPane);

 (450, 400);

 (false);

 (EXIT_ON_CLOSE);

 (false);

 (false);

 (false);

 (false);

 (new ActionListener() {

 public void actionPerformed(ActionEvent e) { etEditable(true);

 textAllocation[i][j].setEditable(true); textAvailable[j].setEditable(true);

 }

 }

 }

 });

 (new ActionListener() {

 public void actionPerformed(ActionEvent e) { Init();

 (true);

 });

 (new ActionListener() {

 public void actionPerformed(ActionEvent e) { count = 0;

 SafeSequence = new int[processNum]; worked = new int[resourceNum];

 Finish = new boolean[processNum]; copyVector(worked, available); Safety(0);

 (" 安全序列数量: " + count);

 if (flag) {

 (" 当前系统状态:安全 ");

 (true);

 (true);

 (true);

 for (int i = 0; i < resourceNum; i++) { textRequest[i].setEditable(true);

 }

 } else {

 (" 当前系统状态:不安全 ");

 }

 }

 }

 }

 (false);

 }

 });

 (new ActionListener() {

 public void actionPerformed(ActionEvent e) { count = 0;

 for (int i = 0; i < processNum; i++) {

 Finish[i] = false;

 }

 ("");

 flag = false;

 RequestResource();

 }

 });

 (new ActionListener() {

 public void actionPerformed(ActionEvent e) { /*

 * (""); ("");

 */

 (false);

 ("");

 for (int i = 0; i < processNum; i++) { for (int j = 0; j < resourceNum; j++) { textNeed[i][j].setText(""); textAllocation[i][j].setText(""); textAvailable[j].setText(""); textRequest[j].setText(""); etEditable(false); etEditable(false); etEditable(false); textRequest[j].setEditable(false); ("");

 Finish[i] = false;

 }

 }

 flag = false;

 (false); etText());

 }

 max = new int[processNum][resourceNum]; allocated = new int[processNum][resourceNum]; need = new int[processNum][resourceNum];

 for (int i = 0; i < processNum; i++) {

 for (int j = 0; j < resourceNum; j++) {

 max[i][j] = (textNeed[i][j].getText()); allocated[i][j] = (textAllocation[i][j] .getText());

 }

 }

 for (int i = 0; i < resourceNum; i++)

 for (int j = 0; j < processNum; j++)

 need[j][i] = max[j][i] - allocated[j][i];

 for (int i = 0; i < resourceNum; i++) for (int j = 0; j < processNum; j++) { available[i] -= allocated[j][i];

 if (available[i] < 0) {

 (" 您输入的数据有误 ,请重新输入 ");

 }

 }

 }

 void Safety(int n) etText());

 }

 if (!Smaller(request, need[processname])) { (" 资源请求不符该进程的需求量 .");

 } else if (!Smaller(request, available)) {

 ("

 (" 可用资源不足以满足请求 , 进程需要等待 .");

 ("

 (" 可用资源不足以满足请求 , 进程需要等待 .");

 } else {

 Sub(available, request);

 Add(allocated[processname], request);

 Sub(need[processname], request);

 copyVector(worked, available);

 Safety(0);

 if (flag) {

 (" 可立即分配给该进程 !");

 } else {

 (" 分配后导致系统处于不安全状态 !, 不可立即分配 ");

 Add(available, request);

 Sub(allocated[processname], request);

 Add(need[processname], request);

 }

 }

 // }

 }

 }

 五、实验结果:

 初始界面: 初始化:

 检测安全性:

 请求资源:

 (1)进程 2( 1,0,2)

 (2)进程 5( 3,3,0)

 (3)进程 1( 0,2,0)

 六、 遇到的问题及不足之处:

 1、程序编写的时候规定最大资源数和最大进程数均 <=6。

 2、程序直接初始化了 6 个进程框,既浪费了内存空间,又对可视化界 面的美观造成影响。

 3、未对输入异常进行处理:比如在请求资源的第一个方框中只能填入 进程的数字编号,当填入的为非整数时,程序会抛出异常。

 4、未解决进程名中对字符串的处理,直接固定进程名为数字,用户不 能直接输入原有的进程名,造成不好的用户体验。

推荐访问:死锁 银行家 算法 操作系统 利用