银行家算法
- 实验要求
编程实现银行家算法。 - 流程图
- 代码
import threading
import time
import datetime
import numpy as np
from copy import deepcopy
class Process:
def __init__(self, id:int,allocation:np.ndarray,need:np.ndarray):
self.id = id
self.allocation = allocation
self.need = need
self.isfinish = False
def request(self,request:np.ndarray):
global available
if self.isfinish:
raise Exception('Error! Process {} has finished!'.format(hex(self.id)))
elif (self.need<request).any():
raise Exception('Error! Request is larger than the process need')
elif (available<request).any():
print('Error! Request is larger than the available')
return False
else:
self.allocation += request
self.need -= request
available -= request
if checksafe(print=True):
print("If accept it the system will be Safe.")
if (self.need==0).all():
self.isfinish = True
return True
else:
print("If accept it the system will be Dangerous.")
self.allocation -= request
self.need += request
available += request
return False
def checksafe(print=False):
global available
global processes
available_bak = deepcopy(available)
processes_bak = deepcopy(processes)
p_list = []
for _ in range(len(processes_bak)):
all_finish = True
for process in processes_bak:
if process.isfinish:
continue
elif (process.need<=available_bak).all():
available_bak += process.allocation
process.need -= process.need
process.allocation -= process.allocation
process.isfinish = True
p_list.append(hex())
break
else:
all_finish = False
if print:
printtable(available=available_bak,processes=processes_bak)
if all_finish:
printtable(available=available,processes=processes)
return True
else:
return False
def banker():
if checksafe():
print('The initial system is safe')
while (ans:=input('Do you want continue?(Yy/Nn)')) and ans in 'Yy':
while True:
try:
pid = int(input('Please input the process id:'),16)
try:
process = processes[pid2index[pid]]
except:
print('Error! The process id is not exist')
raise Exception()
break
except:
print('Please input a correct number!')
while True:
try:
request = np.array(input('Please input the request:'\
).split(' '),dtype=int)
break
except:
print('Please input a number!')
try:
if not process.request(request):
break
except Exception as e:
print(e)
continue
else:
print('The initial system is not safe')
def printtable(available,processes):
print('\n')
print('Available:',available)
print('\n')
for process in processes:
print('Process',hex(),'allocation:',\
process.allocation,'need:',process.need)
num_processes = np.random.randint(5,20)
available = np.random.randint(num_processes-5,num_processes+5,size=3)
processes = []
pid2index = {}
for i in range(num_processes):
processes.append(Process(id=np.random.randint(0,1e9),\
allocation=np.random.randint(1,10,size=3),\
need=np.random.randint(1,10,size=3)))
pid2index[processes[i].id] = i
banker()
- 模拟优化
- 初始资源数随机生成
- 后续资源申请需要用户手动输入(不然太容易直接不安全或者直接申请资源错误)
- 充足的异常处理避免用户输错
- 运行方式
python exp3.py
- 运行结果
- 运行结果分析
- 一开始系统处于安全状态
- 进程0xc1530e7申请资源5 0 0后系统仍处于安全状态,剩余资源为[2 4 6]刚好与进程0x20a75e03所需资源一致,并且之后可以产生安全序列
- 进程0x12d3f5cb申请资源1 0 0后系统处于不安全状态,剩余资源为[1 4 6],小于进程0xc1530e7所需资源