Python實現銀行家算法

銀行家算法就不用再介紹了,直接上代碼:

import copy

#初始化函數
def bank_init():
    Process = [0]


#安全性算法函數
def bank_safe(Available,Need,Allocation,Pn):
    #創建Work數組 初始值爲Avaliable
    Work = copy.deepcopy(Available)
    #創建Finish數組  默認設爲全0 (False)
    Finish = [0]*Pn
    #創建安全序列
    safeSequence = []
    #大循環5次
    count = 0
    while count<Pn:
        # 按進程編號順序找到一個可加入安全序列的進程,即滿足Finish[i]=False
        # 且Needi <= Work 的進程Pi,則假設該進程不久將完成任務
        i = 0  # 進程下標
        while i < Pn:
            isSafe = True  # 記錄當前進程是否可以加入安全序列
            # 如果該進程finish值爲0(False)
            if not Finish[i]:
                # 比較Need[i]與Work的各元素值
                for ch in Work.keys():
                    # 如果需求大於可用
                    if Need[i][ch] > Work[ch]:
                        isSafe = False
                # for循環之後根據isSafe判斷該進程是否可以加入安全序列
                if isSafe:  # isSafe爲True說明可以加入安全序列
                    safeSequence.append(i+1)  # 加入安全序列
                    Finish[i] = True  # 將此進程的finish值設爲True
                    for ch2 in Work.keys():
                        # Work = Work+Allocation[i]
                        Work[ch2] = Work[ch2] + Allocation[i][ch2]
            i += 1  # 結束本次循環,開始判斷下一個進程
        count += 1 # 開始下一輪判斷
    #判斷安全序列裏面的元素個數,如果等於進程數Pn 說明安全,輸出安全序列
    if len(safeSequence) ==Pn:
        print("系統處於安全狀態,計算得出安全序列:",safeSequence)
        return True
    #不安全  返回False
    print("系統處於不安全狀態,資源請求失敗")
    return False


#模擬進程請求資源函數
#傳入進程序號和請求request字典
def bank_request(processId,requestDict):
    print("接收到請求時分配情況Allocate:", Allocation)
    #第一步:如果請求的資源數是否超過它所需要的最大值
    for ch in requestDict.keys():
        # 如果請求資源數超過它所需要的最大值
        if requestDict[ch] > Need[processId-1][ch]:
            print("由於請求數超過最大值,請求資源被拒絕!")
            return False #返回錯誤
    #第二步:判斷請求資源與可用資源的關係
    for ch2 in requestDict.keys():
        # 如果無足夠資源
        if requestDict[ch2] > Available[ch2]:
            print("由於可用資源不足,請求資源被拒絕!")
            return False #返回錯誤

     # 第三步:分配資源
    for ch3 in requestDict.keys():
        #Available[j] = Available[j] - Requesti[j]
        Available[ch3] = Available[ch3] - requestDict[ch3]
    #Allocation[i,j] = Allocation[i,j] + Requesti[j]
    allo = Allocation[processId-1]
    for ch4 in allo.keys():
        allo[ch4] = allo[ch4] +requestDict[ch4]
    #Need[i, j] = Need[i, j] - Requesti[j]
    need = Need[processId - 1]
    for ch5 in need.keys():
        need[ch5] = need[ch5] - requestDict[ch5]


    #第四步:進行系統執行安全性檢查,如果爲安全狀態,分配成功,否則還原到分配前的狀態
    if  bank_safe(Available,Need,Allocation,Pn):
        print("請求完成時分配情況Allocate:", Allocation)
    else:
        # 還原到分配前的狀態
        for ch3 in requestDict.keys():
            # Available[j] = Available[j] + Requesti[j]
            Available[ch3] = Available[ch3] + requestDict[ch3]
        # Allocation[i,j] = Allocation[i,j] - Requesti[j]
        allo = Allocation[processId - 1]
        for ch4 in allo.keys():
            allo[ch4] = allo[ch4] - requestDict[ch4]
        # Need[i, j] = Need[i, j] + Requesti[j]
        need = Need[processId - 1]
        for ch5 in need.keys():
            need[ch5] = need[ch5] + requestDict[ch5]

    return Allocation

#計算Need數組
def bank_need(Allocation,Max):
    Need = []
    cn = 0
    for allo in Allocation:
        tmp = copy.deepcopy(allo)  # 深拷貝一個同規格字典用於存放need
        for ch in allo.keys():
            tmp[ch] = Max[cn][ch] - allo[ch]
        Need.append(tmp)
        cn += 1
    return Need

#更新Available數組
def bank_Available(Available,Allocation):
    for allo in Allocation:
        for ch in allo.keys():
            Available[ch] =Available[ch] -  allo[ch]
    return Available


if __name__ == '__main__':
    print("---------本程序用於演示銀行家算法---------")
    print("---------即將開始收集初始數據,請按提示操作---------' ")

    # 得到進程數量Pn,作爲參數創建進程列表
    Pn = int(input("請輸入要模擬的進程數量n:"))
    # 得到可利用資源向量Available
    Available = eval(input("請輸入系統初始資源信息,輸入格式爲dict,如'{'A':10, 'B':10, 'C':10}' :"))
    # 得到輸入每個進程對每種資源的最大需求、已經獲得的數量、每種類型資源的數目
    print("---------即將開始輸入Max的信息---------' ")
    Max = []
    for i in range(1,Pn+1):
        print("請輸入第",i,"個進程對每種資源的最大需求,輸入格式爲dict,如'{'A':1, 'B':2, 'C':3}' ")
        max = eval(input(" :"))
        Max.append(max)
    print("---------即將開始輸入Allocation的信息---------' ")
    Allocation = []
    for i in range(1,Pn+1):
        print("請輸入第",i,"個進程對每種資源的已佔用的情況,輸入格式爲dict,如'{'A':1, 'B':2, 'C':3}' ")
        allo = eval(input(" :"))
        Allocation.append(allo)

    #Pn = 5
    #Available = {'A':17, 'B':5, 'C':20}
    # Max = [{'A':5, 'B':5, 'C':9},
    #               {'A':5, 'B':3, 'C':6},
    #               {'A':4, 'B':0, 'C':11},
    #               {'A':4, 'B':2, 'C':5},
    #              {'A':4, 'B':2, 'C':4}]
    # Allocation = [{'A':2, 'B':1, 'C':2},
    #                     {'A':4, 'B':0, 'C':2},
    #                    {'A':4, 'B':0, 'C':5},
    #                    {'A':2, 'B':0, 'C':4},
    #                    {'A':3, 'B':1, 'C':4}]
    print("---------計算得到初次分配後的Need矩陣---------' ")
    Need =bank_need(Allocation, Max)#計算得到初次分配後的need矩陣
    print("---------計算得到初次分配後的Available數組---------' ")
    bank_Available(Available,Allocation)#計算得到初次分配後的Available字典

    while True:
        print("---------模擬進程請求資源請輸入1---------")
        print("---------對系統當前狀態進行診斷請輸入2---------")
        print("---------查看當前資源分配情況請輸入3---------")
        print("---------退出程序請輸入quit---------")
        x = input('請輸入執行的功能序號x:')#提示輸入
        if x == '1':
            print("---------即將開始模擬進程請求資源---------")
            processId = int(input("請輸入要模擬的進程序號n:"))
            requestDict = eval(input("請輸入請求資源信息,輸入格式如'{'A':10, 'B':10, 'C':10}' :"))
            bank_request(processId, requestDict) #模擬請求資源
            print("---------模擬進程請求資源已結束---------")
        elif x == '2':
            print("---------即將開始診斷當前系統狀態---------")
            bank_safe(Available, Need, Allocation, Pn)
            print("---------診斷當前系統狀態已結束---------")
        elif x == '3':
            print("---------當前資源分配情況如下---------")
            print(Allocation)
        elif x=='quit':
            print('程序結束運行')
            break
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章