2024年华为OD机试真题-简易内存池 C/C++解法

使用链表记录已分配的内存起始地址和大小,后续分配和释放基于此链表

#include <iostream>
#include <string>
#include <algorithm>
#include <list>

using namespace std;

// 简易内存池
static void HuaWei_OD_test25(void)
{
    // 请求分配指定大小内存时,如果分配成功,返回分配到的内存首地址;
    // 如果内存不足,或指定的大小为0,则输出error。
    // 释放掉之前分配的内存时,释放成功无需输出,如果释放不存在的首地址则输出error。

    int cmd_cnt;
    cin >> cmd_cnt;

#define REQUEST_CMD 0
#define RELEASE_CMD 1

    // 命令序列,这里pair的first代表了命令类型,0为申请,1为释放
    // pair的second,对于request代表了申请内存的大小,
    // 对于release代表了释放内存的首地址
    vector<pair<int, int>> cmd_vec;

    for (int i = 0; i < cmd_cnt; i++)
    {
        string cmd;
        cin >> cmd;

        auto find_delim = cmd.find('=', 0);
        string val_str = cmd.substr(find_delim + 1, -1);
        int val = atoi(val_str.c_str()); // 获得值

        if (cmd.find("REQUEST") != string::npos)
        {
            // 内存申请命令
            cmd_vec.push_back(std::make_pair(REQUEST_CMD, val));
        }
        else if (cmd.find("RELEASE") != string::npos)
        {
            // 内存释放命令
            cmd_vec.push_back(std::make_pair(RELEASE_CMD, val));
        }
    }

    // 记录成功分配的内存首地址和大小
    struct little_mem
    {
        int start_addr;
        int size;
    };

    list<little_mem> mem_allocate_list;

    for (int i = 0; i < cmd_vec.size(); i++)
    {
        // 释放操作
        if (cmd_vec[i].first == RELEASE_CMD)
        {
            // 释放不存在的首地址输出 error
            auto match_pos = std::find_if(
                mem_allocate_list.begin(), mem_allocate_list.end(),
                [=](const little_mem &mem)
                {
                    if (mem.start_addr == cmd_vec[i].second)
                        return true;                  
                    return false; });

            // 当内存成功申请列表为空,或者找不到此命令对应内存的起始地址
            if (mem_allocate_list.empty() || match_pos == mem_allocate_list.end())
            {
                cout << "error\n";
            }
            else
            {
                // 成功释放,将对应申请内存记录从mem_allocate_list排除
                mem_allocate_list.erase(match_pos);
            }
        }

        // 申请操作
        else if (cmd_vec[i].first == REQUEST_CMD)
        {
            // 如果申请内存大小为0,输出error
            if (cmd_vec[i].second == 0)
            {
                cout << "error\n";
            }

            // 当此时申请内存大小超出限制,输出error
            if (cmd_vec[i].second > 100)
            {
                cout << "error\n";
            }

            int start_base = 0; // 内存申请起始地址

            for (const auto &mem : mem_allocate_list)
            {
                // 如果[start_base, start_base + cmd_vec[i].second]
                // 与[mem.start_addr, mem.start_addr + mem.size]
                // 有重合则start_base向后移

                // 区域交叉情况1
                bool cross_1 = (start_base + cmd_vec[i].second > mem.start_addr &&
                                start_base + cmd_vec[i].second <= mem.start_addr + mem.size);

                // 区域交叉情况2
                bool cross_2 = (start_base >= mem.start_addr &&
                                start_base <= mem.start_addr + mem.size);

                if (cross_1 || cross_2)
                {
                    start_base = mem.start_addr + mem.size;
                }
            }

            if (start_base + cmd_vec[i].second < 100)
            {
                cout << start_base << endl;
                little_mem new_mem;
                new_mem.start_addr = start_base;
                new_mem.size = cmd_vec[i].second;
                mem_allocate_list.push_back(new_mem);
            }
        }
    }
}

int main()
{
    HuaWei_OD_test25();
    return 0;
}

  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值