实验一、编制银行家算法通用程序,并检测所给状态的系统安全性。假定系统的任何一种资源在任一时刻只能被一个进程使用。任何进程已经占用的资源只能由进程自己释放,而不能由其它进程抢占。进程申请的资源不能满足时,必须等待。
设计的要求:
(1) 程序中使用的数据结构及主要符号说明;
(2) 资源的种类和数目可以变化的
(3) 进程可以任意的顺序创建和变化
#!/usr/bin/env python
# -*- coding: utf-8 -*
'''
该模块实现了银行家算法,可以有效地避免死锁。
算法思想:
每一个进程在进入系统时,它必须申明在运行过程中,可能需要每种资源类型地最大单元数目
1) 其数目不应超过系统所拥有地资源总量
2)当请求资源时,系统必须首先确定是否有足够的资源分配给进程
3)计算将这些资源分配给进程后,是否会使系统处于不安全状态
模块功能:
在用户可视化界面上,用户可以根据自己的需求,输入请求资源的进程名称和进程请求的资源数,
点击CHECK按钮,系统会提示用户请求资源的结果。其中,资源的种类和数目是可以变化的,进程
可以任意的创建和变化,资源可以任意的顺序创建和变化。
'''
import numpy as np
import sys
from PyQt5.QtWidgets import QDesktopWidget, QHBoxLayout, QVBoxLayout
from PyQt5.QtGui import QBrush,QPixmap,QPalette,QIcon
from PyQt5.QtWidgets import (QLabel, QGridLayout)
from PyQt5.QtWidgets import (QWidget, QPushButton, QLineEdit, QApplication)
def safeAlgorithm():
#安全性检查算法
global safeList, system_security
safeList= []
work = Available
Finish=[False]*length_progress
#在进程集合中找到一个 Finish[i] = false 且 need[i,j] < Work[j] 的进程
while False in Finish:
for i in range(0,length_progress):
for j in range(0,length_Avalable):
if (Finish[i] == False) and (Need[i]<=work).all():
for m in range(length_Avalable):
work[m] = work[m]+ Allocation[i][m]
Finish[i] = True
safeList.append(i)
else:
break
#如果所有进程的finish[i] = true 都满足,则表示系统处于安全状态;否则,系统处于不安全状态。
if False in Finish:
system_security = "不安全状态"
print("*"*45)
print("您输入的请求资源数:{}".format(Request))
print("您输入的请求进程是{}".format(Request_name))
print("系统安全性:不安全状态")
print("*"*45)
else:
system_security = "系统安全"
print("*"*45)
print("您输入的请求进程是{}".format(Request_name))
print("您输入的请求资源数:{}".format(Request))
print("系统安全性:系统安全")
print("安全序列为:",safeList)
print("*"*45)
#银行家算法的流程
def BankerAlgorithm():
global Allocation,Available,Max,Need,safeList,Request,Request_name, system_security
if (Request<=Need[Request_name]).all():
if (Request<=Available).all(): #vector.all()表示矩阵每一项都相等
Available -=Request
Need[Request_name] -= Request
Allocation[Request_name] +=Request
safeAlgorithm()
else:
system_security = "请求超出可利用的资源,请等待"
print("请求超出可利用的资源,请等待")
else:
system_security = "所需要的资源已超过它所宣布的最大值"
print("所需要的资源已超过它所宣布的最大值")
#初始化各数据结构
#可利用各资源总数
Available = np.array([3,3,2])
length_Avalable = len(Available)
#各进程最大需求资源数
Max = np.array([[7,5,3],[3,2,2],[9,0,2],[2,2,2],[4,3,3]])
length_progress = len(Max)
print(length_Avalable)
#已分配各进程的资源数
Allocation = np.array([[0,1,0],[2,0,0],[3,0,2],[2,1,1],[0,0,2]])
#各进程尚需的资源数
Need = np.array([[7,4,3],[1,2,2],[6,0,0],[0,1,1],[4,3,1]])
#安全进程执行序列
safeList=[]
#各进程对各资源的请求
Request=[]
#进程名称
Request_name=""
system_security = ""
class banker(QWidget):
'''
·用户界面
'''
def __init__(self):
super().__init__()
self.initUI()
self.setIcon()
def setIcon(self):
palette1 = QPalette()
palette1.setBrush(self.backgroundRole(), QBrush(QPixmap("icon/androidBackground.jpg"))) # 设置背景图片
self.setPalette(palette1)
self.setWindowIcon(QIcon("icon/iconbook.png"))
def initUI(self):
#左边的一列
self.identifier_label = QLabel('您输入的请求进程是: [0,1,2,3,4] ')
self.request_label = QLabel('您输入的请求资源数量是:')
self.security_label = QLabel('系统安全性是:')
self.sequece_label = QLabel('安全序列是:')
#设置开始的按钮
self.check_btn = QPushButton('check', self)
self.check_btn.clicked.connect(self.function)
#右边的一列
self.identifier_lineEdit = QLineEdit(self)
self.security_lineEdit = QLineEdit(self)
self.sequece_lineEdit = QLineEdit(self)
self.request_lineEdit_1 = QLineEdit(self)
self.request_lineEdit_2 = QLineEdit(self)
self.request_lineEdit_3 = QLineEdit(self)
#请求数输入的参数
self.sub_layout = QHBoxLayout()
self.sub_layout.addWidget(self.request_lineEdit_1)
self.sub_layout.addWidget(self.request_lineEdit_2)
self.sub_layout.addWidget(self.request_lineEdit_3)
self.main_layout = QGridLayout()
self.main_layout.addWidget(self.identifier_label,0,0)
self.main_layout.addWidget(self.identifier_lineEdit,0,1)
self.main_layout.addWidget(self.request_label, 1, 0)
self.main_layout.addItem (self.sub_layout,1,1)
self.main_layout.addWidget(self.security_label, 2, 0)
self.main_layout.addWidget(self.security_lineEdit, 2, 1)
self.main_layout.addWidget(self.sequece_label, 3, 0)
self.main_layout.addWidget(self.sequece_lineEdit, 3, 1)
self.main_layout.addWidget(self.check_btn, 4,1)
self.setLayout(self.main_layout)
'''
self.identifier_lineEdit = QLineEdit(self)
#self.numberOfProcess.move(130, 22)
self.sub_layout = QHBoxLayout()
self.sub_layout.addWidget(self.check_btn)
self.sub_layout.addWidget(self.identifier_lineEdit)
self.main_layout = QVBoxLayout()
self.main_layout.addWidget(self.identifier_label)
self.main_layout.addLayout(self.sub_layout)
'''
self.setGeometry(300, 300, 600, 400)
self.setWindowTitle('Input dialog')
self.show()
def function(self):
global Request_name, Request, safeList, system_security
Request_name = [int(self.identifier_lineEdit.text())]
Request = np.array([int(self.request_lineEdit_1.text()), int(self.request_lineEdit_2.text()), int(self.request_lineEdit_3.text())])
BankerAlgorithm()
self.sequece_lineEdit.setText(str(safeList))
self.security_lineEdit.setText(system_security)
def center(self):
frame_geometry = self.frameGeometry()
center_geometry = QDesktopWidget().availableGeometry().center()
frame_geometry.moveCenter(center_geometry)
self.move(frame_geometry.topLeft())
def init_widgets(self):
# Main layout
self.main_layout = QVBoxLayout()
# Winner Display
self.identifier_label = QLabel('Input participants...')
# Participant Inputs
self.participant_layout = QVBoxLayout()
# Head
self.participant_head_layout = QHBoxLayout()
self.participant_label = QLabel('Participants:')
self.participant_add = QPushButton('Add')
# Inputs
self.participant_inputs = []
# Controls
self.control_layout = QHBoxLayout()
self.start_button = QPushButton('Start')
self.stop_button = QPushButton('Stop')
self.stop_button.setEnabled(False)
if __name__ =="__main__":
app = QApplication(sys.argv)
ex = banker()
sys.exit(app.exec_())
本文介绍了一种基于银行家算法的死锁避免方案,并通过Python实现了一个交互式的程序来帮助用户理解算法的工作原理。用户可以在图形界面上输入请求资源的进程名和所需资源数,系统则会反馈资源请求的结果及当前的安全状态。
3523

被折叠的 条评论
为什么被折叠?



