Pyforms 模拟内存管理模型

匿名 (未验证) 提交于 2019-12-03 00:26:01

环境 Python 3.6.3 + Pyforms 3.0.0

模拟:

内存管理模型的设计与实现

对内存的可变分区申请采用链表法管理进行模拟实现。要求:

设计思想

约定内存页数为16(索引地址为0-15),进程用字典表示,键是进程的标识符,值是进程的起始地址和占用内存页数。

每当有新的进程申请,检测内存中是否有足够的剩余空间,若没有,则紧缩内存,再次检查,若还是没有空间则输出失败信息;若有,根据选择的算法进行内存空间分配

变量和方法

主要变量:

self.lastAddress 记录上一次分配的内存地址,用于邻近适度算法。

self.processes 记录进程信息,包括进程的进程名、起始地址和大小。

主要方法:

getEmptyBlocks 获取空闲区域的起始地址和大小,函数会遍历整个内存,记录连续出现的‘N’(表示该页空闲)的位置和长度。

tightening 紧缩内存空间,从内存索引为0开始重新赋予进程起始地址,并根据起始地址更新GUI。

apply 申请进程,从GUI获取进程的名字和大小,检查内存剩余空间是否满足进程需求,满足需求时根据不同算法调度内存空间。算法见下:

首次适度算法:从头遍历getEmptyBlocks返回的记录(数据类型为列表),找到第一个满足要求的索引,从该索引更新进程信息。

最优适度算法:从getEmptyBlocks返回的数据中减去进程需求,找到最小值对应的索引,从该索引更新进程信息。

邻近适度算法,遍历getEmptyBlocks返回的数据,第一次从索引大于self.lastAddress的索引中查找满足条件的索引,若找到,从该索引更新进程信息;否则,从头开始查找。

运行截图

程序初始化

第一行表示内存页地址

第二行表示该页是否为空(N表示空)


分别申请进程名为a、b、c、d、e,内存大小都为3的进程,算法使用首次适度算法


查询内存使用状态


撤销进程a、b、d,采用最优适度算法申请大小为3的进程f



重置内存,分别申请进程名为a、b、c的3个进程,进程大小都为3,采用首次适度算法



撤销进程a,采用邻近适度算法申请大小为3的进程d



通过内存紧缩,申请大小为6的进程e


查询内存使用状态


import pyforms from pyforms import BaseWidget from pyforms.controls import *   class Memory(BaseWidget):      def __init__(self):         super(Memory, self).__init__("内存分配模拟器")         # 进程字典         # 键值对为编号和实例         self.processes = dict()         # GUI         # 查询页         self.textArea = ControlTextArea('内存使用情况')         # 管理页         # 第一行 内存地址         self.memoryMark_0 = ControlLabel('0')         self.memoryMark_1 = ControlLabel('1')         self.memoryMark_2 = ControlLabel('2')         self.memoryMark_3 = ControlLabel('3')         self.memoryMark_4 = ControlLabel('4')         self.memoryMark_5 = ControlLabel('5')         self.memoryMark_6 = ControlLabel('6')         self.memoryMark_7 = ControlLabel('7')         self.memoryMark_8 = ControlLabel('8')         self.memoryMark_9 = ControlLabel('9')         self.memoryMark_10 = ControlLabel('10')         self.memoryMark_11 = ControlLabel('11')         self.memoryMark_12 = ControlLabel('12')         self.memoryMark_13 = ControlLabel('13')         self.memoryMark_14 = ControlLabel('14')         self.memoryMark_15 = ControlLabel('15')         # 第二行 内存使用进程标记         self.memoryUser_0 = ControlLabel('')         self.memoryUser_1 = ControlLabel('')         self.memoryUser_2 = ControlLabel('')         self.memoryUser_3 = ControlLabel('')         self.memoryUser_4 = ControlLabel('')         self.memoryUser_5 = ControlLabel('')         self.memoryUser_6 = ControlLabel('')         self.memoryUser_7 = ControlLabel('')         self.memoryUser_8 = ControlLabel('')         self.memoryUser_9 = ControlLabel('')         self.memoryUser_10 = ControlLabel('')         self.memoryUser_11 = ControlLabel('')         self.memoryUser_12 = ControlLabel('')         self.memoryUser_13 = ControlLabel('')         self.memoryUser_14 = ControlLabel('')         self.memoryUser_15 = ControlLabel('')         self.memoryUser = [self.memoryUser_0, self.memoryUser_1, self.memoryUser_2, self.memoryUser_3,                            self.memoryUser_4, self.memoryUser_5, self.memoryUser_6, self.memoryUser_7,                            self.memoryUser_8, self.memoryUser_9, self.memoryUser_10, self.memoryUser_11,                            self.memoryUser_12, self.memoryUser_13, self.memoryUser_14, self.memoryUser_15                            ]         self.memoryUserMark = [False] * 16         for i in self.memoryUser:             i.value = 'N'         # 第三行 进程申请内存         self.applyLabel = ControlLabel('进程申请')         self.applyName = ControlText('进程名')         self.applySpace = ControlText('申请内存大小')         self.applyBtn = ControlButton('申请')         # 第四行 进程撤销         self.deleteLabel = ControlLabel('进程撤销')         self.deleteName = ControlText('进程名')         self.deleteBtn = ControlButton('撤销')         # 第五行 算法选择         self.algorithm = ControlCombo('算法选择')         self.algorithm.add_item('首次适度算法', 0)         self.algorithm.add_item('最优适度算法', 1)         self.algorithm.add_item('邻近适度算法', 2)         # 第六行 查询和重置         self.query = ControlButton('查询')         self.reset = ControlButton('重置')         # 绑定按钮和事件         self.applyBtn.value = self.apply         self.deleteBtn.value = self.delete         self.query.value = self.query_s         self.reset.value = self.setMemoryEmpty         # GUI布局         self.formset = [{             '管理': [(                     'memoryMark_0', 'memoryMark_1', 'memoryMark_2', 'memoryMark_3',                     'memoryMark_4', 'memoryMark_5', 'memoryMark_6', 'memoryMark_7',                     'memoryMark_8', 'memoryMark_9', 'memoryMark_10', 'memoryMark_11',                     'memoryMark_12', 'memoryMark_13', 'memoryMark_14', 'memoryMark_15'                     ),                    (                        'memoryUser_0', 'memoryUser_1', 'memoryUser_2', 'memoryUser_3',                        'memoryUser_4', 'memoryUser_5', 'memoryUser_6', 'memoryUser_7',                        'memoryUser_8', 'memoryUser_9', 'memoryUser_10', 'memoryUser_11',                        'memoryUser_12', 'memoryUser_13', 'memoryUser_14', 'memoryUser_15',                    ),                 ('applyLabel', 'applyName', 'applySpace', 'applyBtn'),                 ('deleteLabel', 'deleteName', 'deleteBtn'),                 ('algorithm'),                 ('query', 'reset')             ],             '查询':['textArea']         }]         # 上次分配地址         self.lastAddress = 0      # 获取空闲内存页     def getEmptyBlocks(self):         blocks = list()         i = 0         while i < 16:             if self.memoryUser[i].value == 'N':                 size = 1                 blocks.append(i)                 while i < 15:                     i += 1                     if self.memoryUser[i].value == 'N':                         size += 1                     else:                         blocks.append(size)                         break             i += 1         if len(blocks) & 1 == 1:             temp = blocks[len(blocks)-1]             blocks.append(16-temp)         return blocks      # 用进程名更新进程占用的内存页     def changeMemory(self, name, index, size):         for i in range(index, index+size):             self.memoryUser[i].value = name      # 撤销进程后重置对应内存页为空     def resetMemory(self, index, size):         for i in range(index, index+size):             self.memoryUser[i].value = 'N'      # 重置数据为空     def setMemoryEmpty(self):         for i in range(16):             self.memoryUser[i].value = 'N'         self.processes = dict()         self.lastAddress = 0      # 紧缩     def tightening(self):         for i in range(16):             self.memoryUser[i].value = 'N'         lastIndex = 0         for i in self.processes:             process = self.processes[i]             process[0] = lastIndex             self.changeMemory(i, process[0], process[1])             self.lastAddress = lastIndex             lastIndex += process[1]      # 进程申请     def apply(self):         blocks = self.getEmptyBlocks()         index = list()         size = list()         for i in range(int(len(blocks)/2)):             index.append(blocks[i*2])             size.append(blocks[i*2+1])         need = int(self.applySpace.value)         name = self.applyName.value         # 若剩余空间不满足申请要求则紧缩         if need > max(size):             self.tightening()         # 在紧缩的基础上若剩余空间不满足申请要求则输出失败信息         blocks = self.getEmptyBlocks()         index = list()         size = list()         for i in range(int(len(blocks)/2)):             index.append(blocks[i*2])             size.append(blocks[i*2+1])         need = int(self.applySpace.value)         name = self.applyName.value         if need > max(size):             s = '进程'             s += name             s += '申请失败\n'             s += '当前最大空闲区域页数为'             s += str(max(size))             self.textArea.value = s         # 若满足申请要求则根据选择的算法进行分配         else:             # 首次适度算法             if self.algorithm.value == 0:                 for i in range(len(index)):                     if need <= size[i]:                         self.changeMemory(name, index[i], need)                         self.processes[name] = [index[i], need]                         self.lastAddress = index[i]                         break             # 最优适度算法             elif self.algorithm.value == 1:                 bestSize = [i - need for i in size]                 size = []                 for i in bestSize:                     if i >= 0:                         size.append(i)                 bestIndex = 0                 bestMin = 16                 for i in range(len(size)):                     if bestMin > size[i]:                         bestMin = size[i]                         bestIndex = i                 self.changeMemory(name, index[bestIndex], need)                 self.processes[name] = [index[bestIndex], need]                 self.lastAddress = index[bestIndex]             # 邻近适度算法             else:                 compare = self.lastAddress                 for i in range(len(index)):                     if compare <= index[i] and need <= size[i]:                         self.changeMemory(name, index[i], need)                         self.processes[name] = [index[i], need]                         self.lastAddress = index[i]                         return                 for i in range(len(index)):                     if need <= size[i]:                         self.changeMemory(name, index[i], need)                         self.processes[name] = [index[i], need]                         self.lastAddress = index[i]      # 进程撤销     def delete(self):         name = self.deleteName.value         if name in self.processes:             process = self.processes[name]             del self.processes[name]             self.resetMemory(process[0], process[1])      # 查询     def query_s(self):         showValue = ''         for i in self.processes:             process = self.processes[i]             s = '进程名:' + i             s += '\t起始地址:'             s += str(process[0])             s += '\t进程大小:'             s += str(process[1])             s += '\n'             showValue += s         self.textArea.value = showValue   if __name__ == "__main__":     pyforms.start_app(Memory)



标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!