先决条件:内存管理中的分区分配方法
在“分区分配”中,当有多个可用分区来自由容纳一个进程请求时,必须选择一个分区。为了选择特定的分区,需要一种分区分配方法。如果避免内部碎片,则分区分配方法被认为更好。
考虑以下数据进行处理:
Process No. | Process Size |
---|---|
1 | 88 |
2 | 192 |
3 | 277 |
4 | 365 |
5 | 489 |
Memory Block No. | Memory Block Size |
---|---|
1 | 400 |
2 | 500 |
3 | 300 |
4 | 200 |
5 | 100 |
以下是各种分区分配方案及其相对于上述给定数据的实现。
1.首先适合
此方法保留按内存位置(从低位到高位内存)组织的作业的忙/闲列表。在这种方法中,第一作业要求具有大于或等于其大小的空间的第一可用内存。操作系统不会搜索适当的分区,而只是将作业分配给具有足够大小的最近的可用内存分区。
以下是首次拟合算法的实现:
// C++ program for the implementation
// of the First Fit algorithm
#include
#include
#include
using namespace std;
// Process Class
class process {
public:
// Size & number of process
size_t size;
pid_t no;
};
// Memory Class
class memory {
public:
size_t size;
// Number of memory & queue of space
// occupied by process
pid_t no;
queue space_occupied;
// Function to push process in a block
void push(const process p)
{
if (p.size <= size) {
space_occupied.push(p);
size -= p.size;
}
}
// Function to pop and return the
// process from the block
process pop()
{
process p;
// If space occupied is empty
if (!space_occupied.empty()) {
p = space_occupied.front();
space_occupied.pop();
size += p.size;
return p;
}
}
// Function to check if block is
// completely empty
bool empty()
{
return space_occupied.empty();
}
};
// Function to get data of processess
// allocated using first fit
vector first_fit(vector memory_blocks,
queue processess)
{
int i = 0;
bool done, done1;
memory na;
na.no = -10;
while (!processess.empty()) {
done = 0;
for (i = 0; i < memory_blocks.size(); i++) {
done1 = 0;
if (memory_blocks.at(i).size
>= processess.front().size) {
memory_blocks.at(i).push(processess.front());
done = 1;
done1 = 1;
break;
}
}
// If process is done
if (done == 0 && done1 == 0) {
na.size += processess.front().size;
na.push(processess.front());
}
// pop the process
processess.pop();
}
if (!na.space_occupied.empty())
memory_blocks.push_back(na);
return memory_blocks;
}
// Function to display the allocation
// of all processess
void display(vector memory_blocks)
{
int i = 0, temp = 0;
process p;
cout << "+-------------+--------------+--------------+"
<< endl;
cout << "| Process no. | Process size | Memory block |"
<< endl;
cout << "+-------------+--------------+--------------+"
<< endl;
// Traverse memory blocks size
for (i = 0; i < memory_blocks.size(); i++) {
// While memory block size is not empty
while (!memory_blocks.at(i).empty()) {
p = memory_blocks.at(i).pop();
temp = to_string(p.no).length();
cout << "|" << string(7 - temp / 2 - temp % 2, ' ')
<< p.no << string(6 - temp / 2, ' ')
<< "|";
temp = to_string(p.size).length();
cout << string(7 - temp / 2 - temp % 2, ' ')
<< p.size
<< string(7 - temp / 2, ' ') << "|";
temp = to_string(memory_blocks.at(i).no).length();
cout << string(7 - temp / 2 - temp % 2, ' ');
// If memory blocks is assigned
if (memory_blocks.at(i).no != -10) {
cout << memory_blocks.at(i).no;
}
// Else memory blocks is assigned
else {
cout << "N/A";
}
cout << string(7 - temp / 2, ' ')
<< "|" << endl;
}
}
cout << "+-------------+--------------+--------------+"
<< endl;
}
// Driver Code
int main()
{
// Declare memory blocks
vector memory_blocks(5);
// Declare first fit blocks
vector first_fit_blocks;
// Declare queue of all processess
queue processess;
process temp;
// Set sample data
memory_blocks[0].no = 1;
memory_blocks[0].size = 400;
memory_blocks[1].no = 2;
memory_blocks[1].size = 500;
memory_blocks[2].no = 3;
memory_blocks[2].size = 300;
memory_blocks[3].no = 4;
memory_blocks[3].size = 200;
memory_blocks[4].no = 5;
memory_blocks[4].size = 100;
temp.no = 1;
temp.size = 88;
// Push the process
processess.push(temp);
temp.no = 2;
temp.size = 192;
// Push the process
processess.push(temp);
temp.no = 3;
temp.size = 277;
// Push the process
processess.push(temp);
temp.no = 4;
temp.size = 365;
// Push the process
processess.push(temp);
temp.no = 5;
temp.size = 489;
// Push the process
processess.push(temp);
// Get the data
first_fit_blocks = first_fit(memory_blocks, processess);
// Display the data
display(first_fit_blocks);
memory_blocks.clear();
memory_blocks.shrink_to_fit();
first_fit_blocks.clear();
first_fit_blocks.shrink_to_fit();
return 0;
}
输出:
+-------------+--------------+--------------+
| Process no. | Process size | Memory block |
+-------------+--------------+--------------+
| 1 | 88 | 1 |
| 2 | 192 | 1 |
| 3 | 277 | 2 |
| 4 | 365 | N/A |
| 5 | 489 | N/A |
+-------------+--------------+--------------+
2.下一个适合
下一个契合度是“首次契合度”的修改版本。它首先是找到一个可用分区的开始,但是在下次调用时,它将从中断的地方开始搜索,而不是从头开始。该策略使用了漫游指针。指针沿着存储链移动以搜索下一个拟合。这有助于避免总是从空闲块链的开头(开头)开始使用内存。
以下是Next Fit算法的实现:
// C++ program for the implementation
// of the Next Fit algorithm
#include
#include
#include
using namespace std;
// Process Class
class process {
public:
// Size & number of process
size_t size;
pid_t no;
};
// Memory Class
class memory {
public:
size_t size;
// Number of memory & queue of space
// occupied by process
pid_t no;
queue space_occupied;
// Function to push process in a block
void push(const process p)
{
if (p.size <= size) {
space_occupied.push(p);
size -= p.size;
}
}
// Function to pop and return the
// process from the block
process pop()
{
process p;
// If space occupied is empty
if (!space_occupied.empty()) {
p = space_occupied.front();
space_occupied.pop();
size += p.size;
return p;
}
}
// Function to check if block is
// completely empty
bool empty()
{
return space_occupied.empty();
}
};
// Function to get data of processess
// allocated using Next Fit
vector next_fit(vector memory_blocks,
queue processess)
{
int i = 0;
bool done, done1;
memory na;
na.no = -10;
// Loop till process is empty
while (!processess.empty()) {
done1 = 0;
// Traverse memory_blocks
for (i = 0; i < memory_blocks.size(); i++) {
done = 0;
// If process is not empty
if (!processess.empty() && memory_blocks.at(i).size >= processess.front().size) {
memory_blocks.at(i).push(processess.front());
done = 1;
done1 = 1;
processess.pop();
}
}
if (!processess.empty() && done == 0 && done1 == 0) {
na.size += processess.front().size;
na.push(processess.front());
processess.pop();
}
}
// If space is not occupied push
// the memory_blocks na
if (!na.space_occupied.empty()) {
memory_blocks.push_back(na);
}
return memory_blocks;
}
// Function to display the allocation
// of all processess
void display(vector memory_blocks)
{
int i = 0, temp = 0;
process p;
cout << "+-------------+--------------+--------------+"
<< endl;
cout << "| Process no. | Process size | Memory block |"
<< endl;
cout << "+-------------+--------------+--------------+"
<< endl;
// Traverse memory blocks size
for (i = 0; i < memory_blocks.size(); i++) {
// While memory block size is not empty
while (!memory_blocks.at(i).empty()) {
p = memory_blocks.at(i).pop();
temp = to_string(p.no).length();
cout << "|" << string(7 - temp / 2 - temp % 2, ' ')
<< p.no << string(6 - temp / 2, ' ')
<< "|";
temp = to_string(p.size).length();
cout << string(7 - temp / 2 - temp % 2, ' ')
<< p.size
<< string(7 - temp / 2, ' ') << "|";
temp = to_string(memory_blocks.at(i).no).length();
cout << string(7 - temp / 2 - temp % 2, ' ');
// If memory blocks is assigned
if (memory_blocks.at(i).no != -10) {
cout << memory_blocks.at(i).no;
}
// Else memory blocks is assigned
else {
cout << "N/A";
}
cout << string(7 - temp / 2, ' ')
<< "|" << endl;
}
}
cout << "+-------------+--------------+--------------+"
<< endl;
}
// Driver Code
int main()
{
// Declare memory blocks
vector memory_blocks(5);
// Declare next fit blocks
vector next_fit_blocks;
// Declare queue of all processess
queue processess;
process temp;
// Set sample data
memory_blocks[0].no = 1;
memory_blocks[0].size = 400;
memory_blocks[1].no = 2;
memory_blocks[1].size = 500;
memory_blocks[2].no = 3;
memory_blocks[2].size = 300;
memory_blocks[3].no = 4;
memory_blocks[3].size = 200;
memory_blocks[4].no = 5;
memory_blocks[4].size = 100;
temp.no = 1;
temp.size = 88;
// Push the process
processess.push(temp);
temp.no = 2;
temp.size = 192;
// Push the process
processess.push(temp);
temp.no = 3;
temp.size = 277;
// Push the process
processess.push(temp);
temp.no = 4;
temp.size = 365;
// Push the process
processess.push(temp);
temp.no = 5;
temp.size = 489;
// Push the process
processess.push(temp);
// Get the data
next_fit_blocks = next_fit(memory_blocks,
processess);
// Display the data
display(next_fit_blocks);
memory_blocks.clear();
memory_blocks.shrink_to_fit();
next_fit_blocks.clear();
next_fit_blocks.shrink_to_fit();
return 0;
}
输出:
+-------------+--------------+--------------+
| Process no. | Process size | Memory block |
+-------------+--------------+--------------+
| 1 | 88 | 1 |
| 2 | 192 | 2 |
| 3 | 277 | 3 |
| 4 | 365 | N/A |
| 5 | 489 | N/A |
+-------------+--------------+--------------+
3.最差的身材
最差拟合为分区分配一个进程,该进程在主内存中可用的可用分区中最大。如果较大的进程在以后出现,则内存将没有空间容纳它。
以下是最差拟合算法的实现:
// C++ program for the implementation
// of the Worst Fit algorithm
#include
#include
#include
using namespace std;
// Process Class
class process {
public:
// Size & number of process
size_t size;
pid_t no;
};
// Memory Class
class memory {
public:
size_t size;
// Number of memory & queue of space
// occupied by process
pid_t no;
queue space_occupied;
// Function to push process in a block
void push(const process p)
{
if (p.size <= size) {
space_occupied.push(p);
size -= p.size;
}
}
// Function to pop and return the
// process from the block
process pop()
{
process p;
// If space occupied is empty
if (!space_occupied.empty()) {
p = space_occupied.front();
space_occupied.pop();
size += p.size;
return p;
}
}
// Function to check if block is
// completely empty
bool empty()
{
return space_occupied.empty();
}
};
// Function to get data of processess
// allocated using Worst Fit
vector worst_fit(vector memory_blocks,
queue processess)
{
int i = 0, index = 0, max;
memory na;
na.no = -10;
// Loop till process queue is not empty
while (!processess.empty()) {
max = 0;
// Traverse the memory_blocks
for (i = 0; i < memory_blocks.size(); i++) {
if (memory_blocks.at(i).size >= processess.front().size
&& memory_blocks.at(i).size > max) {
max = memory_blocks.at(i).size;
index = i;
}
}
if (max != 0) {
memory_blocks.at(index).push(processess.front());
}
else {
na.size += processess.front().size;
na.push(processess.front());
}
// Pop the current process
processess.pop();
}
// If space is not occupied
if (!na.space_occupied.empty()) {
memory_blocks.push_back(na);
}
// Return the memory
return memory_blocks;
}
// Function to display the allocation
// of all processess
void display(vector memory_blocks)
{
int i = 0, temp = 0;
process p;
cout << "+-------------+--------------+--------------+"
<< endl;
cout << "| Process no. | Process size | Memory block |"
<< endl;
cout << "+-------------+--------------+--------------+"
<< endl;
// Traverse memory blocks size
for (i = 0; i < memory_blocks.size(); i++) {
// While memory block size is not empty
while (!memory_blocks.at(i).empty()) {
p = memory_blocks.at(i).pop();
temp = to_string(p.no).length();
cout << "|" << string(7 - temp / 2 - temp % 2, ' ')
<< p.no << string(6 - temp / 2, ' ')
<< "|";
temp = to_string(p.size).length();
cout << string(7 - temp / 2 - temp % 2, ' ')
<< p.size
<< string(7 - temp / 2, ' ') << "|";
temp = to_string(memory_blocks.at(i).no).length();
cout << string(7 - temp / 2 - temp % 2, ' ');
// If memory blocks is assigned
if (memory_blocks.at(i).no != -10) {
cout << memory_blocks.at(i).no;
}
// Else memory blocks is assigned
else {
cout << "N/A";
}
cout << string(7 - temp / 2, ' ')
<< "|" << endl;
}
}
cout << "+-------------+--------------+--------------+"
<< endl;
}
// Driver Code
int main()
{
// Declare memory blocks
vector memory_blocks(5);
// Declare worst fit blocks
vector worst_fit_blocks;
// Declare queue of all processess
queue processess;
process temp;
// Set sample data
memory_blocks[0].no = 1;
memory_blocks[0].size = 400;
memory_blocks[1].no = 2;
memory_blocks[1].size = 500;
memory_blocks[2].no = 3;
memory_blocks[2].size = 300;
memory_blocks[3].no = 4;
memory_blocks[3].size = 200;
memory_blocks[4].no = 5;
memory_blocks[4].size = 100;
temp.no = 1;
temp.size = 88;
// Push the process
processess.push(temp);
temp.no = 2;
temp.size = 192;
// Push the process
processess.push(temp);
temp.no = 3;
temp.size = 277;
// Push the process
processess.push(temp);
temp.no = 4;
temp.size = 365;
// Push the process
processess.push(temp);
temp.no = 5;
temp.size = 489;
// Push the process
processess.push(temp);
// Get the data
worst_fit_blocks = worst_fit(memory_blocks,
processess);
// Display the data
display(worst_fit_blocks);
memory_blocks.clear();
memory_blocks.shrink_to_fit();
worst_fit_blocks.clear();
worst_fit_blocks.shrink_to_fit();
return 0;
}
输出:
+-------------+--------------+--------------+
| Process no. | Process size | Memory block |
+-------------+--------------+--------------+
| 3 | 277 | 1 |
| 1 | 88 | 2 |
| 2 | 192 | 2 |
| 4 | 365 | N/A |
| 5 | 489 | N/A |
+-------------+--------------+--------------+
4.最合适
此方法按大小从小到大的顺序排列忙/闲列表。在这种方法中,操作系统首先根据给定作业的大小搜索整个内存,然后将其分配给内存中最适合的空闲分区,从而使其能够有效地使用内存。这里的工作按从最小到最大的顺序排列。
以下是最佳拟合算法的实现:
// C++ program for the implementation
// of the Best Fit algorithm
#include
#include
#include
using namespace std;
// Process Class
class process {
public:
// Size & number of process
size_t size;
pid_t no;
};
// Memory Class
class memory {
public:
size_t size;
// Number of memory & queue of space
// occupied by process
pid_t no;
queue space_occupied;
// Function to push process in a block
void push(const process p)
{
if (p.size <= size) {
space_occupied.push(p);
size -= p.size;
}
}
// Function to pop and return the
// process from the block
process pop()
{
process p;
// If space occupied is empty
if (!space_occupied.empty()) {
p = space_occupied.front();
space_occupied.pop();
size += p.size;
return p;
}
}
// Function to check if block is
// completely empty
bool empty()
{
return space_occupied.empty();
}
};
// Function to get data of processess
// allocated using Best Fit
vector best_fit(vector memory_blocks,
queue processess)
{
int i = 0, min, index = 0;
memory na;
na.no = -10;
// Loop till processe is not empty
while (!processess.empty()) {
min = 0;
// Traverse the memory_blocks
for (i = 0; i < memory_blocks.size(); i++) {
if (memory_blocks.at(i).size >= processess.front().size && (min == 0 || memory_blocks.at(i).size < min)) {
min = memory_blocks.at(i).size;
index = i;
}
}
if (min != 0) {
memory_blocks.at(index).push(processess.front());
}
else {
na.size += processess.front().size;
na.push(processess.front());
}
// Pop the processe
processess.pop();
}
// If space is no occupied then push
// the current memory na
if (!na.space_occupied.empty()) {
memory_blocks.push_back(na);
}
// Return the memory_blocks
return memory_blocks;
}
// Function to display the allocation
// of all processess
void display(vector memory_blocks)
{
int i = 0, temp = 0;
process p;
cout << "+-------------+--------------+--------------+"
<< endl;
cout << "| Process no. | Process size | Memory block |"
<< endl;
cout << "+-------------+--------------+--------------+"
<< endl;
// Traverse memory blocks size
for (i = 0; i < memory_blocks.size(); i++) {
// While memory block size is not empty
while (!memory_blocks.at(i).empty()) {
p = memory_blocks.at(i).pop();
temp = to_string(p.no).length();
cout << "|" << string(7 - temp / 2 - temp % 2, ' ')
<< p.no << string(6 - temp / 2, ' ')
<< "|";
temp = to_string(p.size).length();
cout << string(7 - temp / 2 - temp % 2, ' ')
<< p.size
<< string(7 - temp / 2, ' ') << "|";
temp = to_string(memory_blocks.at(i).no).length();
cout << string(7 - temp / 2 - temp % 2, ' ');
// If memory blocks is assigned
if (memory_blocks.at(i).no != -10) {
cout << memory_blocks.at(i).no;
}
// Else memory blocks is assigned
else {
cout << "N/A";
}
cout << string(7 - temp / 2, ' ')
<< "|" << endl;
}
}
cout << "+-------------+--------------+--------------+"
<< endl;
}
// Driver Code
int main()
{
// Declare memory blocks
vector memory_blocks(5);
// Declare best fit blocks
vector best_fit_blocks;
// Declare queue of all processess
queue processess;
process temp;
// Set sample data
memory_blocks[0].no = 1;
memory_blocks[0].size = 400;
memory_blocks[1].no = 2;
memory_blocks[1].size = 500;
memory_blocks[2].no = 3;
memory_blocks[2].size = 300;
memory_blocks[3].no = 4;
memory_blocks[3].size = 200;
memory_blocks[4].no = 5;
memory_blocks[4].size = 100;
temp.no = 1;
temp.size = 88;
// Push the processe to queue
processess.push(temp);
temp.no = 2;
temp.size = 192;
// Push the processe to queue
processess.push(temp);
temp.no = 3;
temp.size = 277;
// Push the processe to queue
processess.push(temp);
temp.no = 4;
temp.size = 365;
// Push the processe to queue
processess.push(temp);
temp.no = 5;
temp.size = 489;
// Push the processe to queue
processess.push(temp);
// Get the data
best_fit_blocks = best_fit(memory_blocks,
processess);
// Display the data
display(best_fit_blocks);
memory_blocks.clear();
memory_blocks.shrink_to_fit();
best_fit_blocks.clear();
best_fit_blocks.shrink_to_fit();
return 0;
}
输出:
+-------------+--------------+--------------+
| Process no. | Process size | Memory block |
+-------------+--------------+--------------+
| 4 | 365 | 1 |
| 5 | 489 | 2 |
| 3 | 277 | 3 |
| 2 | 192 | 4 |
| 1 | 88 | 5 |
+-------------+--------------+--------------+
想要从精选的最佳视频中学习并解决问题,请查看有关从基础到高级C++的C++基础课程以及有关语言和STL的C++ STL课程。要完成从学习语言到DS Algo等的更多准备工作,请参阅“完整面试准备课程” 。