首次适应法-FF和最佳适应法-BF实现内存分配
用首次适应算法实现内存分配与回收

用首次适应算法实现内存分配与回收首次适应算法(First Fit)是一种常用的内存分配算法,它将内存分为若干个大小相等的块,并按顺序进行分配。
当有一个进程请求内存时,首次适应算法从头开始,找到第一个大小能够满足这个进程需要的空闲块,将其分配给该进程。
以下是使用首次适应算法实现内存分配与回收的一种简单示例:1.假设整个内存大小为M字节,每个块的大小为N字节,内存被分为M/N个块。
2. 定义一个长度为(M/N)的布尔数组block,表示每个块的分配状态,初始时所有元素都为false,表示空闲状态。
3. 当一个进程请求分配S字节的内存时,首次适应算法从第一个块开始遍历数组block,直到找到一个大小大于等于S的空闲块。
4. 如果找到了合适的空闲块,将该块标记为已分配(设置为true),并返回该块的起始地址;否则,返回分配失败的标识。
5. 当一个进程释放已分配的内存时,可以根据该内存的起始地址计算出对应的块索引,将对应的block元素设置为false,表示该块变为空闲状态。
以下是一个简单的C++代码示例,演示了使用首次适应算法进行内存分配与回收的实现:```cpp#include <iostream>using namespace std;const int M = 1000; // 总内存大小const int N = 100; // 块大小bool block[M/N] = { false }; // 内存块分配状态//首次适应内存分配算法int allocateMemory(int size)int numBlocks = M / N; // 块数量int numNeeded = size / N;if (size % N != 0)numNeeded++;}for (int i = 0; i < numBlocks; i++)bool found = true;for (int j = i; j < i + numNeeded; j++)if (j >= numBlocks , block[j] == true)found = false;break;}}if (found)for (int j = i; j < i + numNeeded; j++)block[j] = true;}return i * N;}}return -1; // 分配失败//内存回收void deallocateMemory(int startAddr, int size)int startIndex = startAddr / N;int numBlocks = size / N;if (size % N != 0)numBlocks++;}for (int i = startIndex; i < startIndex + numBlocks; i++) block[i] = false;}int maiint size1 = 200; // 请求200字节内存int size2 = 300; // 请求300字节内存int addr1 = allocateMemory(size1);int addr2 = allocateMemory(size2);if (addr1 != -1)cout << "分配内存成功,起始地址:" << addr1 << endl; } elsecout << "分配内存失败" << endl;}if (addr2 != -1)cout << "分配内存成功,起始地址:" << addr2 << endl; } elsecout << "分配内存失败" << endl;}deallocateMemory(addr1, size1);deallocateMemory(addr2, size2);return 0;```这段代码实现了一个简单的内存分配与回收示例。
可变分区存储管理的内存分配算法模拟实现----最佳适应算法

可变分区存储管理的内存分配算法模拟实现----最佳适应算法可变分区存储管理是一种内存管理技术,其通过将内存分割成不同大小的区域来存储进程。
每个进程被分配到与其大小最匹配的区域中。
内存分配算法的选择影响了系统的性能和资源利用率。
本文将介绍最佳适应算法,并模拟实现该算法。
一、什么是最佳适应算法?最佳适应算法是一种可变分区存储管理中的内存分配策略。
它的基本思想是在每次内存分配时选择最合适的空闲区域。
具体来说,它从可用的空闲区域中选择大小与需要分配给进程的内存最接近的区域。
二、算法实现思路最佳适应算法实现的关键是如何快速找到最合适的空闲区域。
下面给出一个模拟实现的思路:1. 初始化内存分区列表,首先将整个内存定义为一个大的空闲区域。
2. 当一个进程请求分配内存时,从列表中找到与所需内存最接近的空闲区域。
3. 将该空闲区域分割成两部分,一部分分配给进程,并将该部分标记为已分配,另一部分留作新的空闲区域。
4. 更新内存分区列表。
5. 当一个进程释放内存时,将其所占用的内存区域标记为空闲,然后尝试合并相邻的空闲区域。
三、算法模拟实现下面是一个简单的Python代码实现最佳适应算法:pythonclass MemoryPartition:def __init__(self, start_addr, end_addr, is_allocated=False): self.start_addr = start_addrself.end_addr = end_addrself.is_allocated = is_allocatedclass MemoryManager:def __init__(self, total_memory):self.total_memory = total_memoryself.partition_list = [MemoryPartition(0, total_memory)]def allocate_memory(self, process_size):best_fit_partition = Nonesmallest_size = float('inf')# 找到最佳适应的空闲区域for partition in self.partition_list:if not partition.is_allocated and partition.end_addr - partition.start_addr >= process_size:if partition.end_addr - partition.start_addr < smallest_size:best_fit_partition = partitionsmallest_size = partition.end_addr - partition.start_addrif best_fit_partition:# 将空闲区域分割,并标记为已分配new_partition =MemoryPartition(best_fit_partition.start_addr,best_fit_partition.start_addr + process_size, True)best_fit_partition.start_addr += process_sizeself.partition_list.append(new_partition)return new_partition.start_addr,new_partition.end_addrelse:return -1, -1def deallocate_memory(self, start_addr, end_addr):for partition in self.partition_list:if partition.start_addr == end_addr and not partition.is_allocated:# 标记空闲区域partition.is_allocated = False# 尝试合并相邻空闲区域for next_partition in self.partition_list:if not next_partition.is_allocated andnext_partition.start_addr == end_addr:end_addr = next_partition.end_addrself.partition_list.remove(next_partition)breakelse:breakdef print_partitions(self):for partition in self.partition_list:if partition.is_allocated:print(f"Allocated Partition: {partition.start_addr} - {partition.end_addr}")else:print(f"Free Partition: {partition.start_addr} - {partition.end_addr}")# 测试最佳适应算法if __name__ == "__main__":mm = MemoryManager(1024)start, end = mm.allocate_memory(256)print(f"Allocated memory: {start} - {end}")mm.print_partitions()mm.deallocate_memory(start, end)print("Memory deallocated:")mm.print_partitions()以上代码实现了一个简单的内存管理器类`MemoryManager`,它具有`allocate_memory`和`deallocate_memory`等方法。
首次适应算法,最佳适应算法,最坏适应算法

首次适应算法,最佳适应算法,最坏适应算法首次适应算法、最佳适应算法和最坏适应算法是常见的内存分配算法,也是操作系统中重要的实现方式。
首次适应算法是向空闲区域分配内存时,按照空闲区域的起始地址从小到大进行扫描,找到第一个可以分配的空闲区域,然后将其分配给请求者。
虽然该算法简单易懂,但不断扫描空闲区域会大大降低操作系统的效率。
同时,由于内存释放会产生内存碎片,首次适应算法效果也会逐渐变差。
最佳适应算法是相对于首次适应算法而言的。
它是在空闲区域中寻找最小可用空间,尽可能满足分配请求。
该算法不会一遍遍扫描空闲区域,因此效率更高。
但随着分配请求增多,内存碎片也会不断增加,最佳适应算法将面临“Eureka”陷阱,即为了满足分配请求而不得不“铺平”内存分配空间,导致后续分配请求无法得到满足。
最坏适应算法是在空闲区域中寻找最大可用空间,分配请求时尽可能让内存块留有足够大的空间,防止内存碎片增多。
该算法的效率较低,因为会在所有空闲区域中查找最大空间;但相比较首次适应算法和最佳适应算法,他避免了内存碎片的问题。
总之,以上三种算法都有自己的优点和缺点,为了更好地利用内存资源,可以根据实际情况选择适合的算法。
同时,需要及时对内存进行整理、清理和释放,保证内存的健康状态,提高操作系统的运行效率。
首次适应算法和最佳适应算法【讲解】

首次适应算法和最佳适应算法是动态存储分配解决方案研究的内容,所以本文对这两种算法的讨论是通过研究动态存储管理来进行的。
一、存储管理的基本问题:存储管理讨论的基本问题是:1)、系统如何应用户的“请求”执行内存分配动作?2)、系统如何对用户不再使用后“释放”的内存执行回收动作,以保证为新的“用户请求”提供内存分配?内存的分配可以以静态方式进行,内存空间被分割为固定大小的若干内存块,用户的请求到达只要找到一块空闲的内存块予以分配即可,很显然静态存储分配的好处主要是实现比较方便,效率高,程序执行中系统需要做的事情比较简单。
然而实际情况下提出“请求”的用户可能是进入系统的一个作业,也可能是程序执行过程中的一个动态变量。
“请求”需要获得的内存容量大小不一,这种做法造成了对程序大小的严格的限制,使某些问题不能够合理的解决,此外,也会造成内存空间的浪费。
动态存储管理就是确定如何满足一个个内存“请求”,如何更合理的使用有限的内存空间的一种内存分配解决方案,它以能够依据用户的请求依次进行内存空间的分配和回收,能够尽可能少的使用有限的空闲内存空间,最大限度的保证后续“请求”的可满足性为最终目的。
二、关于动态分配方案的分析:通常我们将已分配给用户是用的一段连续的内存空间称为“占用块”,将未分配给任何用户的一段连续的内存空间称为“可利用空间块”或者“空闲块”,我们在这里的描述将使用“占用块”和“空闲块”这两个概念。
整个内存区在没有任何用户进入和运行的情况下只有一个空闲块,即整个可供用户“请求”使用的用户内存区域。
随着不断的有用户请求进入系统,并依次获得系统为其分配的内存,使得整个内存区域逐渐被分割成两大部分:低地址区域包含若干占用块;高低址区域是空闲内存区域。
经过一段时间后,有的用户运行结束,它们所占用的内存区释放后转变为一个个空闲块,这就使整个内存区域呈现出占用块和空闲块交错相隔的状态。
而此时,如果再有新的用户“请求”到达,那么,系统如何为这个“请求”进行内存分配呢?在肯定动态存储管理的前提下,我们可以采取两种方案解决这个问题,一种解决方案是系统继续把高地址的空闲块分配给用户,而不理会低地址区域是否有结束执行的用户释放的内存块,直到剩余的高地址区域的空闲块不能满足新的用户“请求”,分配操作无法再进行下去时,才去回收结束执行的用户释放的内存块,并重新组织内存,进而完成内存分配。
B u d d y 伙 伴 算 法 ( 2 0 2 0 )

内存分配算法——FF、BF、WF、buddy(伙伴算法)分区分配算法:首次适应算法(First Fit):从空闲分区表的第一个表目起查找该表,把最先能够满足要求的空闲区分配给作业,这种方法的目的在于减少查找时间。
为适应这种算法,空闲分区表(空闲区链)中的空闲分区要按地址由低到高进行排序。
该算法优先使用低址部分空闲区,在低址空间造成许多小的空闲区,在高地址空间保留大的空闲区。
最佳适应算法(Best Fit):从全部空闲区中找出能满足作业要求的、且大小最小的空闲分区,这种方法能使碎片尽量小。
为适应此算法,空闲分区表(空闲区链)中的空闲分区要按从小到大进行排序,自表头开始查找到第一个满足要求的自由分区分配。
该算法保留大的空闲区,但造成许多小的空闲区。
最差适应算法(Worst Fit):从全部空闲区中找出能满足作业要求的、且大小最大的空闲分区,从而使链表中的结点大小趋于均匀,适用于请求分配的内存大小范围较窄的系统。
为适应此算法,空闲分区表(空闲区链)中的空闲分区按大小从大到小进行排序,自表头开始查找到第一个满足要求的自由分区分配。
该算法保留小的空闲区,尽量减少小的碎片产生。
伙伴算法(buddy):使用二进制优化的思想,将内存以2的幂为单位进行分配,合并时只能合并是伙伴的内存块,两个内存块是伙伴的三个条件是:1.大小相等(很好判断)2.地址连续(也很好判断)3.两个内存块分裂自同一个父块(其实只要判断低地址的内存块首地址是否是与父块地址对齐,即合并后的首地址为父块大小的整数倍)使用lowbit等位运算可以o(1)判断。
伙伴算法在实现的时候可以使用数组+链表的形式(有点像邻接表那种),因为内存上限是固定的,比较容易确定。
下列代码使用的是二维链表(写起来就没有数组加链表简洁)。
在分配调整内存块时使用了递归,如果需要提高效率可以改为循环(递归更能体现出思想且代码简单,循环效率更高但是复杂一丢丢,自行选取)。
#includebits-stdc++.husing namespace std;-*进程分配内存块链表的首指针*-struct allocated_block *allocated_block_head = NULL;#define PROCESS_NAME_LEN 32 -*进程名长度*-#define MIN_SLICE 10 -*最小碎片的大小*-#define DEFAULT_MEM_SIZE 1024 -*内存大小*-#define DEFAULT_MEM_START 0 -*起始位置*--* 内存分配算法 *-#define MA_FF 1--first fit#define MA_BF 2#define MA_WF 3#define Buddy 4 --伙伴算法-*描述每一个空闲块的数据结构*-struct free_block_type{int size;int start_addr;struct free_block_type *next;typedef struct free_block_type FB;-*指向内存中空闲块链表的首指针*-struct free_block_type *free_block;--此处尽量按内存地址顺序排列,-*每个进程分配到的内存块的描述*-struct allocated_block{int pid; int size;int start_addr;char process_name[PROCESS_NAME_LEN];struct allocated_block *next;typedef struct allocated_block allocated_block_type;typedef struct b_free_block_typeint size;free_block_type *list;b_free_block_type *next;}b_free_block_type;b_free_block_type *b_free_block=NULL;--空的时候要设置为NULL --end of buddytypedef struct allocated_block AB;int mem_size=DEFAULT_MEM_SIZE; -*内存大小*-int ma_algorithm = Buddy; -*当前分配算法*- --------------------------static int pid = 0; -*初始pid*-int flag = 0; -*设置内存大小标志*---init_free_block(int mem_size);int display_mem_usage();int b_creat_free_blocks(free_block_type *ab);int rearrange_Buddy();int rearrange(int algorithm);int allocate_mem(struct allocated_block *ab);int free_mem(struct allocated_block *ab);int dispose(struct allocated_block *free_ab);int disfree(FB *free_ab);void free_f();void free_b();-*初始化空闲块,默认为一块,可以指定大小及起始地址*-struct free_block_type* init_free_block(int mem_size)free_f();free_b();struct free_block_type *fb;fb=(struct free_block_type *)malloc(sizeof(struct free_block_type));if(fb==NULL){printf("Error.");getchar();return NULL;fb-size = mem_size;fb-start_addr = DEFAULT_MEM_START;fb-next = NULL;free_block=(struct free_block_type *)malloc(sizeof(struct free_block_type));*free_block=*fb;--free_block供rearrange_Buddy使用,会被销毁 rearrange_Buddy();--初始化buddy算法return fb;--会在main中重新赋值free_block-*显示菜单*-void display_menu(){printf("");printf("1 - Set memory size (default=%d)", DEFAULT_MEM_SIZE); printf("2 - Select memory allocation algorithm");printf("3 - New process ");printf("4 - Terminate a process ");printf("5 - Display memory usage ");printf("0 - Exit");-*设置内存的大小*-int set_mem_size(){--只能设置一次, 清除现有所有链表,重新分配 int size;if(flag!=0){ --防止重复设置printf("Cannot set memory size again");return 0;printf("Total memory size =");scanf("%d", size);if(size0) {mem_size = size;-- free_block-size = mem_size;init_free_block(mem_size);return 1;cout"输入不合法"endl;return 0;-* 设置当前的分配算法 *-int set_algorithm(){int algorithm;printf("t1 - First Fit");printf("t2 - Best Fit ");printf("t3 - Worst Fit ");printf("t4 - Buddy ");scanf("%d", algorithm);--按指定算法重新排列空闲区链表if(algorithm==Buddy)if(ma_algorithm!=Buddy)rearrange(algorithm);if(ma_algorithm==Buddy)rearrange(algorithm);if(algorithm=1 algorithm =4)ma_algorithm=algorithm;cout"输入错误!"endl;display_mem_usage();-*按FF算法重新整理内存空闲块链表*-int rearrange_FF(){--请自行补充--将buddy的二级制表示法展开,按地址排序b_free_block_type *p=b_free_block;free_block_type *work,*twork;allocated_block_type*t=(allocated_block_type*)malloc(sizeof(allocated_block_type)); --最后要销毁此临时块--不排除其他函数调用此函数来完成内存列表的切换,需要暂时改变算法,结束之前再进行还原。
首次适应算法、循环首次适应算法、最佳适应算法和最坏适应算法

首次适应算法、循环首次适应算法、最佳适应算法和最坏适应算法是关于操作系统内存管理中内存分配策略的四种典型算法。
以下是对它们的简要解释:1. 首次适应算法(First-fit):在内存分配时,首次适应算法从内存区域的起始部分开始搜索,找到第一个能满足请求大小的空闲内存块,并将其分配给请求者。
首次适应算法的优点是分配速度较快,但可能导致内存空间碎片化。
2. 循环首次适应算法(Next-fit):循环首次适应算法类似于首次适应算法,但它在内存分配时保留上一次搜索的位置。
下一次分配时,算法将从上次停止的位置开始搜索,直到找到合适的空闲内存块或返回到起始位置。
这种方法可以在整个内存空间中分散分配过程,进一步改善内存碎片化问题。
3. 最佳适应算法(Best-fit):最佳适应算法在分配内存时,会查找所有可用的空闲内存块,并分配能够最紧密地满足请求大小的内存块。
该策略试图使分配后的剩余空间尽量小,以减少内存浪费。
然而,最佳适应算法通常需要更多的搜索时间,并可能导致过多的小内存碎片。
4. 最坏适应算法(Worst-fit):最坏适应算法与最佳适应算法相反,它在分配内存时选择最大的可用内存块。
这种策略试图保持较大的连续空闲内存块,以便满足大型请求。
然而,最坏适应算法可能导致大量空间浪费,并需要较长的搜索时间。
这些内存分配算法都有各自的优缺点。
在实际的操作系统实现中,可能会根据需求和上下文使用多种算法的组合来优化内存管理。
首次适应算法、最佳适应算法和最差适应算法

⾸次适应算法、最佳适应算法和最差适应算法关于⾸次适应算法、最佳适应算法和最差适应算法,先看⼀下百度百科的解释,已经说出了三者的最⼤区别。
⾸次适应算法(first-fit):从空闲分区表的第⼀个表⽬起查找该表,把最先能够满⾜要求的空闲区分配给作业,这种⽅法的⽬的在于减少查找时间。
最佳适应算法(best-fit):从全部空闲区中找出能满⾜作业要求的,且⼤⼩最⼩的空闲分区,这种⽅法能使碎⽚尽量⼩。
最差适应算法(worst-fit):它从全部空闲区中找出能满⾜作业要求的、且⼤⼩最⼤的空闲分区,从⽽使链表中的节点⼤⼩趋于均匀。
下⾯看⼀个实例:Given five memory partitions of 100 KB, 500 KB, 200 KB, 300 KB, and 600 KB (in order), how would each of the first-fit, best-fit, and worst-fit algorithms place processes of 212 KB, 417 KB, 112 KB, and 426 KB (in order)? Which algorithm makes the most efficient use of memory?⾸次适应算法:为212k分配空间:依次找寻,找到第⼀个⼤于212k的空闲区;找到第⼆个空闲区500k>212k,分配给212k,剩余288k空闲区;为417k分配空间:依次找寻,找到第⼀个⼤于417k的空闲区;找到第五个空闲区600k>417k,分配给417k,剩余183k空闲区为112k分配空间:依次找寻,找到第⼀个⼤于112k的空闲区;找到第⼆个空闲区288k>112k,分配给112k,剩余176k空闲区为426k分配空间:依次找寻,找到第⼀个⼤于426k的空闲区;未找到,此作业将等待释放空间最佳适应算法:为212k分配空间:找到第⼀个跟212k⼤⼩最接近的空闲区找到第四个空闲区300>212k,剩余88k空闲区为417k分配空间:找到第⼀个跟417k⼤⼩最接近的空闲区找到第⼆个空闲区500>417,剩余83k空闲区为112k分配空间:找到第⼀个跟112k⼤⼩最接近的空闲区找到第三个空闲区200>112k,剩余88k空闲区为426k分配空间:找到第⼀个跟426⼤⼩最接近的空闲区找到第五个空闲区600k>426,剩余74k空闲区最坏适应算法:为212k分配空间:找到第⼀个⼤⼩最⼤的空闲区找到第五个空闲区600>212k,剩余388k空闲区为417k分配空间:找到第⼀个⼤⼩最⼤的空闲区找到第⼆个空闲区500>417,剩余83k空闲区为112k分配空间:找到第⼀个⼤⼩最⼤的空闲区找到第三个空闲区388>112k,剩余276k空闲区为426k分配空间:找到第⼀个⼤⼩最⼤的空闲区达到⼤⼩最⼤的空闲区300k<426k,所以不分配ps:好久没碰操作系统了,今天看到这三个算法的第⼀反应居然有点懵,还是好记性不如烂笔头啊,本⽂中的定义来⾃百度百科,实例题⽬来⾃⽼师布置的作业,答案分析为笔者按⾃⼰的理解写的,若有不对,欢迎指出~~。
c模拟内存分配算法(首次适应算法,最佳适应算法,最坏适应算法)

c模拟内存分配算法(⾸次适应算法,最佳适应算法,最坏适应算法)#include<bits/stdc++.h>using namespace std;/*定义内存的⼤⼩为100*/#define MEMSIZE 100/*如果⼩于此值,将不再分割内存*/#define MINSIZE 2/*内存分区空间表结构*/typedef struct _MemoryInfomation{/*起始地址*/int start;/*⼤⼩*/int Size;/*状态 F:空闲(Free) U:占⽤(Used) E 结束(End)*/char status;} MEMINFO;/*内存空间信息表*/MEMINFO MemList[MEMSIZE];/*显⽰内存状态*/void Display(){int i,used=0;//记录可以使⽤的总空间量printf("\n---------------------------------------------------\n");printf("%5s%15s%15s%15s","Number","start","size","status");printf("\n---------------------------------------------------\n");for(i=0; i<MEMSIZE&&MemList[i].status!='e'; i++){if(MemList[i].status=='u'){used+=MemList[i].Size;}printf("%5d%15d%15d%15s\n",i,MemList[i].start,MemList[i].Size,MemList[i].status=='u'?"USED":"FREE");}printf("\n----------------------------------------------\n");printf("Totalsize:%-10d Used:%-10d Free:%-10d\n",MEMSIZE,used,MEMSIZE-used);}/*初始化所有变量*/void InitMemList(){int i;MEMINFO temp= {0,0,'e'};//初始化空间信息表for(i=0; i<MEMSIZE; i++){MemList[i]=temp;}//起始地址为0MemList[0].start=0;//空间初始为最⼤MemList[0].Size=MEMSIZE;//状态为空闲MemList[0].status='f';}/*最先适应算法*//*算法原理分析:将空闲的内存区按其在储存空间中的起始地址递增的顺序排列,为作业分配储存空间时,从空闲区链的始端开始查找,选择第⼀个满⾜要求的空闲区,⽽不管它究竟有多⼤优点:1.在释放内存分区的时候,如果有相邻的空⽩区就进⾏合并,使其成为⼀个较⼤的空⽩区2.此算法的实质是尽可能的利⽤储存器的低地址部分,在⾼地址部分则保留多的或较⼤的空⽩区,以后如果需要较⼤的空⽩区,就容易满⾜缺点:1.在低地址部分很快集中了许多⾮常⼩的空⽩区,因⽽在空⽩区分配时,搜索次数增加,影响⼯作效率。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
首次适应法和最佳适应法实现内存分配#include<stdio.h>#include<string.h>#include<stdlib.h>#define memory_size 2000;typedef struct Lnode {int state;int fist_adr;//首地址int size; //作业或空闲区大小char name[10];//作业名称struct Lnode *next;} *LinkList;char re_name[10];void Insert_Free(LinkList &p,LinkList &Free)//将作业分配给空闲内存{LinkList L1;L1=(LinkList)malloc (sizeof (Lnode));//生成新节点L1=Free ;if(! L1->next)printf("内存已满,无法分配\n");while(L1->next ){if(p->size <=L1->next->size ) //顺序查找合适的内存空间{if(p->size < L1->next->size ) //作业小于空闲区{L1->next->size=L1->next->size - p->size ;//重置空闲大小p->fist_adr =L1->next->fist_adr; //确地作业的首地址L1->next->fist_adr =L1->next->fist_adr + p->size ;//重置空闲首地址}else //作业等于空闲区,将此空闲区删去{p->fist_adr =L1->next->fist_adr; //确地作业的首地址L1->next =L1->next->next;}break;}else L1 =L1->next;}}void InsertBusy(LinkList p,LinkList &Busy)//插入忙队列{LinkList L;L=Busy->next ;if(L==NULL) //忙队列为空时,即第一次插入作业时{Busy->next=p;p->next=NULL;}else if(p->fist_adr==0){p->next =Busy->next;Busy->next=p;}else{while(L){if(p->fist_adr ==L->fist_adr +L->size ){p->next=L->next;//插入作业L->next=p;}L=L->next;}}}void MLook(LinkList Free,LinkList Busy)//查看内存分配{LinkList F;LinkList B;B=Busy->next ;F=Free->next ;while(B && F){if(B->fist_adr <F->fist_adr ){printf("首地址:%d 大小%d 状态:已分配作业名:%s\n",B->fist_adr ,B->size,B->name );B=B->next;}else{printf("首地址:%d 大小%d 状态:空闲\n",F->fist_adr ,F->size );F=F->next;}}while(B){printf("首地址:%d 大小%d 状态:已分配作业名:%s\n",B->fist_adr ,B->size,B->name );B=B->next;}while(F){printf("始地址:%d 大小%d 状态:空闲\n",F->fist_adr ,F->size );F=F->next;}}void recycle(char re_name[],LinkList &Busy,LinkList &Free)//作业回收{LinkList B;B=Busy;LinkList rey;LinkList F=Free;int k=0;while(B->next){if(!strcmp(re_name,B->next->name))//作业名相等,删去{rey=B->next;//获取删掉作业B->next=B->next->next;break;}else B=B->next;}while(F->next){if(rey->fist_adr < F->next->fist_adr ) //插入空闲区{k=1;if(F->next->fist_adr ==rey->fist_adr +rey->size&& rey->fist_adr !=F->fist_adr +F->size )//合并下空闲区{F->next->fist_adr =F->next->fist_adr -rey->size ;F->next->size =F->next->size +rey->size;}else if(F->fist_adr+F->size == rey->fist_adr &&F->next->fist_adr !=rey->fist_adr +rey->size )//合并上空闲区{F->size =F->size +rey->size ;}else if(F->next->fist_adr ==rey->fist_adr +rey->size && rey->fist_adr ==F->fist_adr +F->size ) //合并作业上下空闲区间{F->size=F->size +rey->size +F->next->size ;F->next=F->next->next;}else{rey->next=F->next;F->next =rey ;}break;}F=F->next;}if(k==0){if(rey->fist_adr==F->fist_adr + F->size)F->size=F->size + rey->size ;else{F->next=rey;// 插入空闲队列尾部rey->next=NULL;}}//BF方法void BF_Insert_Free(LinkList &p,LinkList &Free)//将作业分配给空闲内存{LinkList L1;L1=(LinkList)malloc (sizeof (Lnode));//生成新节点L1=Free ;LinkList F1=Free;LinkList q;q=(LinkList)malloc (sizeof (Lnode));//生成新节点LinkList min;min=(LinkList)malloc (sizeof (Lnode));//生成新节点min->size=10000;//查找适合作业的最小空闲区while(L1->next){if(L1->next->size >= p->size){if((L1->next->size - p->size )<min->size)//将最小空间赋予min{min=L1->next;}}L1=L1->next;}L1=Free;while(L1->next ){if(min==L1->next){if(p->size < L1->next->size ) //作业小于空闲区{L1->next->size=L1->next->size - p->size ;//重置空闲大小p->fist_adr =L1->next->fist_adr; //确地作业的首地址L1->next->fist_adr =L1->next->fist_adr + p->size ;//重置空闲首地址}else //作业等于空闲区,将此空闲区删去{p->fist_adr =L1->next->fist_adr; //确地作业的首地址L1->next =L1->next->next;}break;else L1 =L1->next;}}void main(){LinkList FreeList;//空闲队列LinkList BusyList; //忙队列LinkList p;FreeList=(LinkList)malloc (sizeof (Lnode));//生成新节点,初始化空闲队列,带头结点//初始化空闲队列是整个内存p=(LinkList)malloc (sizeof (Lnode));FreeList->next=p;p->next=NULL;p->size=2000;p->fist_adr =0;BusyList=(LinkList)malloc (sizeof (Lnode));//生成新节点,初始忙队列,带头结点BusyList->next =NULL;int n;printf("选择FF输入1,选择BF输入2:");scanf("%d",&n);if(n==1){printf("输入选择:1-将一新作业装入内存\n 2-将内存中的一个作业回收\n");printf(" 3-查看内存分配\n 4-退出程序\n输入选择:");while(1){scanf("%d",&n);if(n==1){p=(LinkList)malloc (sizeof (Lnode));//生成新作业printf("输入作业名和作业大小");scanf("%s%d",p->name ,&p->size );Insert_Free(p,FreeList); //插入空闲内存InsertBusy(p,BusyList);//插入忙队列}else if(n==2)//将内存中的一个作业回收{printf("输入需要回收的作业名字:");scanf("%s",re_name);recycle(re_name,BusyList,FreeList);}else if(n==3){printf("内存分配情况如下:\n");MLook(FreeList,BusyList);}else if(n==4)//退出程序{exit(0);}printf("输入选择:");}}else if(n==2){printf("输入选择:1-将一新作业装入内存\n 2-将内存中的一个作业回收\n");printf(" 3-查看内存分配\n 4-退出程序\n输入选择:");while(1){scanf("%d",&n);if(n==1){p=(LinkList)malloc (sizeof (Lnode));//生成新作业printf("输入作业名和作业大小");scanf("%s%d",p->name ,&p->size );BF_Insert_Free(p,FreeList); //插入空闲内存InsertBusy(p,BusyList); //插入忙队列}else if(n==2)//将内存中的一个作业回收{printf("输入需要回收的作业名字:");scanf("%s",re_name);recycle(re_name,BusyList,FreeList);}else if(n==3){printf("内存分配情况如下:\n");MLook(FreeList,BusyList);}else if(n==4)//退出程序{exit(0);}printf("输入选择:");}}}。