银行家算法设计与实现
实验内容
假定有多个进程对多种资源进行请求,设计银行家算法的数据结构和程序结构,判定是否存在资源分配的安全序列。使用C语言或Python语言编写程序实现这个算法并进行测试。
主要实现方法和代码介绍
- 编写进程类, 用来存储max, allocation,need等需要的向量.
- 分别编写第一次,第二次输入 和输出的类 .用来格式化的输入数据和输出数据.
- 编写 check方法,检测进程p是否可以进行资源分配, 具体思想就是 :检查need向量小于max-allocation; 检查need是否小于avaliable; 如果是,则返回true;
- 编写深度优先搜索算法dfscheck, 通过深搜的方法检查当前在进程数组中的诸进程是否存在安全序列.
- 在main函数中调用.
程序代码
#include <iostream>
// #include <queue>
using namespace std;
int resourceSpecies;
int avaliable[16];
int aval[16]; //16为系统总资源种类,此向量表示系统可用资源数目.
int pAmount;
class process
{
public:
int pnum;
int max[16];
int allocation[16];
int need[16];
int checked;
int avaliable[16];
};
// queue<process> q;
process p[16];
process prun[16];
int pMustBeAllocationed;
int pmba[16];
void input()
{
cout << "请输入资源种类数目:" << endl;
cin >> resourceSpecies;
cout << "请输入当前系统可分配资源向量:" << endl;
for (int i = 0; i < resourceSpecies; i++)
{
cin >> avaliable[i];
aval[i] = avaliable[i];
}
cout << "请输入进程数目:" << endl;
cin >> pAmount;
for (int i = 0; i < pAmount; i++)
{
// process ptem;
p[i].pnum = i;
p[i].checked = 0;
cout << "请输入第" << i << "个进程的资源最大需求向量:" << endl;
for (int j = 0; j < resourceSpecies; j++)
{
cin >> p[i].max[j];
}
cout << "请输入第" << i << "个进程的资源已分配向量:" << endl;
for (int j = 0; j < resourceSpecies; j++)
{
cin >> p[i].allocation[j];
}
cout << "请输入第" << i << "个进程的资源当前需求向量:" << endl;
for (int j = 0; j < resourceSpecies; j++)
{
cin >> p[i].need[j];
}
}
}
/*测试输入
3
3 3 2
5
6 4 3 1 1 0 5 3 3
3 2 4 2 0 1 1 2 3
9 0 3 4 0 2 5 0 1
2 2 2 2 1 1 0 1 1
3 4 3 0 1 2 3 3 1
4 3 2 1
*/
void output()
{
cout << "存在安全的分配序列,状态安全." << endl;
cout << "\tallocation\tneed\t\tavilable" << endl;
for (int i = 0; i < pAmount; i++)
{
cout << "进程" << prun[i].pnum << "\t" << ends;
for (int j = 0; j < resourceSpecies; j++)
{
cout << prun[i].allocation[j] << " " << ends;
}
cout << "\t" << ends;
for (int j = 0; j < resourceSpecies; j++)
{
cout << prun[i].need[j] << " " << ends;
}
cout << "\t" << ends;
for (int j = 0; j < resourceSpecies; j++)
{
cout << prun[i].avaliable[j] << " " << ends;
}
cout << endl;
}
}
int check(process p)
{
for (int i = 0; i < resourceSpecies; i++)
{
if (p.allocation[i] + p.need[i] > p.max[i])
{
cout << "存在进程当前需求量与已分配量之和大于最大需求量" << endl;
return false;
}
if (p.need[i] > avaliable[i])
{
return false;
}
}
return true;
}
int dfsCheck(int depth)
{
if (depth + 1 > pAmount)
{
return true;
}
for (int i = 0; i < pAmount; i++)
{
if (!p[i].checked && check(p[i]))
{
// for(int j=0;j<resourceSpecies;j++){//分配资源
// avaliable[j]-=p[i].need[j];
// }
for (int j = 0; j < resourceSpecies; j++)
{ //释放资源
avaliable[j] += p[i].allocation[j];
p[i].avaliable[j] = avaliable[j];
}
p[i].checked = 1;
prun[depth] = p[i]; //保存运行顺序;
if (dfsCheck(depth + 1))
{
return true;
}
for (int j = 0; j < resourceSpecies; j++)
{ //若不成立,则放弃这种方案
avaliable[j] -= p[i].allocation[j];
}
p[i].checked = 0;
}
}
return false;
}
void input2()
{
cout << "请输入当前需要分配资源的进程号:" << endl;
cin >> pMustBeAllocationed;
cout << "请输入当前需要分配的资源向量:" << endl;
for (int j = 0; j < resourceSpecies; j++)
{
pmba[j] = p[pMustBeAllocationed].need[j];
cin >> p[pMustBeAllocationed].need[j];
}
for (int j = 0; j < resourceSpecies; j++)
{
avaliable[j] = aval[j];
}
if (check(p[pMustBeAllocationed]))
{
cout << "初始态资源足够分配. "
<< "资源已分配,再次检查是否存在安全序列." << endl;
for (int j = 0; j < resourceSpecies; j++)
{ //占用资源
avaliable[j] -= p[pMustBeAllocationed].need[j];
p[pMustBeAllocationed].allocation[j] += p[pMustBeAllocationed].need[j];
p[pMustBeAllocationed].need[j] = pmba[j] - p[pMustBeAllocationed].need[j];
}
for (int j = 0; j < pAmount; j++)
{
p[j].checked = 0;
}
}
}
int main()
{
input();
if (dfsCheck(0))
{
output();
input2();
if (dfsCheck(0))
{
output();
}
else
{
cout << "此分配方式系统不存在安全序列!" << endl;
}
}
else
{
cout << "系统不存在安全序列!" << endl;
}
return 0;
}
六. 运行结果
- 第一组测例(由老师提供的可行的测例):
- 第二组测例(一开始就不包含正确的执行状态):
- 第三组测例(分配资源后不存在安全序列):
七.结果分析
- 对于第一组测例, 使用老师提供的测例, 可以看到,存在安全序列, 分配顺序已经展示. avaliable是运行后回收后资源的可用资源. 然后输入当前请求资源的进程, 检查是否可行后,进行资源分配, 并再次进行安全序列检查,亦存在,序列顺序如图.
- 对于第二组测例,更改了初始状态的可用资源量,为5 0 1, 此时已经不存在安全序列, 可以看到程序正确得到结果.
- 对于第三组测例,更改了初始状态可用资源量为3 2 2,此时还存在,但是分配后就不存在了,如图可以成功计算.
3628)]
七.结果分析
- 对于第一组测例, 使用老师提供的测例, 可以看到,存在安全序列, 分配顺序已经展示. avaliable是运行后回收后资源的可用资源. 然后输入当前请求资源的进程, 检查是否可行后,进行资源分配, 并再次进行安全序列检查,亦存在,序列顺序如图.
- 对于第二组测例,更改了初始状态的可用资源量,为5 0 1, 此时已经不存在安全序列, 可以看到程序正确得到结果.
- 对于第三组测例,更改了初始状态可用资源量为3 2 2,此时还存在,但是分配后就不存在了,如图可以成功计算.