简易内存池(中)
提示:文章
文章目录
- 前言
- 一、背景
- 二、
- 第二版代码
- 用例2
- 用例3
- 用例4
- 用例5
- 总结
前言
前期疑问:
本文目标:
一、背景
最近
二、
针对上述失败用例,修改代码如下
第二版代码
#include <stdbool.h>
#include <stdio.h>
#include <malloc.h>
#include "securec.h"typedef struct {int start;int end;
} MemoryUint;typedef struct {bool status;int index;
} HashMap;typedef struct {MemoryUint memoryUint[101];HashMap hashMap[101];int hashCount;int unitCount;int memLeftSize;int totalMemorySize;
} MemSystem;static int compare(const void* a, const void* b)
{return ((HashMap*) a)->index - ((HashMap*) b)->index;
}// 注意:该函数为类构造函数,返回的对象指针将作为其他待实现函数的入参;框架代码在调用该函数后,会输出 null(而非指针)
static MemSystem* MemSystemCreate(int space)
{MemSystem* sys = (MemSystem*) malloc(sizeof(MemSystem));if (sys == NULL) {return NULL;}memset_s(sys->memoryUint, sizeof(sys->memoryUint), 0, sizeof(sys->memoryUint));memset_s(sys->hashMap, sizeof(sys->hashMap), 0, sizeof(sys->hashMap));sys->totalMemorySize = space;sys->memLeftSize = space;sys->hashCount = 0;sys->unitCount = 0;return sys;
}static int MemSystemRequest(MemSystem* sys, int size)
{if (size == 0) {return -1;}if (sys->hashCount == 0) {sys->memoryUint[0].start = 0;sys->memoryUint[0].end = sys->memoryUint[0].end + size;sys->hashMap[0].status = true;sys->hashMap[0].index = sys->memoryUint[0].start;sys->hashCount += 1;return sys->memoryUint[0].start;}for (int i = 0; i < sys->hashCount; i++) {if (sys->hashMap[i].status == true) {int spareMemSize = 0;if (sys->hashCount == 1) {if (sys->memoryUint[sys->hashMap[0].index].start > size) {sys->memoryUint[0].start = 0;sys->memoryUint[0].end = sys->memoryUint[0].start + size;sys->hashMap[sys->hashCount].status = true;sys->hashMap[sys->hashCount].index = sys->memoryUint[0].start;sys->hashCount += 1;qsort(sys->hashMap, sys->hashCount, sizeof(HashMap), compare);return sys->memoryUint[0].start;}spareMemSize = sys->totalMemorySize - sys->memoryUint[sys->hashMap[0].index].end;} else {if (sys->memoryUint[sys->hashMap[0].index].start >= size) {sys->memoryUint[0].start = 0;sys->memoryUint[0].end = sys->memoryUint[0].start + size;sys->hashMap[sys->hashCount].status = true;sys->hashMap[sys->hashCount].index = sys->memoryUint[0].start;sys->hashCount += 1;qsort(sys->hashMap, sys->hashCount, sizeof(HashMap), compare);return sys->memoryUint[0].start;}int lastMemInfo = 0;if (sys->hashMap[i + 1].status == false) {lastMemInfo = sys->totalMemorySize;} else {lastMemInfo = sys->hashMap[i + 1].index;}spareMemSize = lastMemInfo - sys->memoryUint[sys->hashMap[i].index].end;}if (spareMemSize >= size) {sys->memoryUint[sys->memoryUint[sys->hashMap[i].index].end].start = sys->memoryUint[sys->hashMap[i].index].end;sys->memoryUint[sys->memoryUint[sys->hashMap[i].index].end].end =sys->memoryUint[sys->memoryUint[sys->hashMap[i].index].end].start + size;if (sys->hashMap[i + 1].status == false) {sys->hashMap[i + 1].status = true;sys->hashMap[i + 1].index = sys->memoryUint[sys->memoryUint[sys->hashMap[i].index].end].start;} else {// 在中间申请内存,hash表中间插入一个key值for (int j = sys->hashCount - 1; j > i; j--) {bool status = sys->hashMap[j].status;int index = sys->hashMap[j].index;sys->hashMap[j + 1].status = status;sys->hashMap[j + 1].index = index;}sys->hashMap[i + 1].status = true;sys->hashMap[i + 1].index = sys->memoryUint[sys->memoryUint[sys->hashMap[i].index].end].start;}sys->hashCount += 1;return sys->memoryUint[sys->memoryUint[sys->hashMap[i].index].end].start;}}}return -1;
}static bool MemSystemRelease(MemSystem* sys, int addr)
{for (int i = 0; i < sys->hashCount; i++) {if (sys->hashMap[i].status == true) {if (sys->memoryUint[sys->hashMap[i].index].start == addr) {sys->hashMap[i].status = false;sys->hashMap[i].index = 0;for (int j = i; j < sys->hashCount; j++) {bool status = sys->hashMap[j + 1].status;int index = sys->hashMap[j + 1].index;sys->hashMap[j].status = status;sys->hashMap[j].index = index;}sys->hashMap[sys->hashCount].status = false;sys->hashMap[sys->hashCount].index = 0;sys->hashCount -= 1;return true;}}}return false;
}static void MemSystemFree(MemSystem* sys)
{free(sys);
}
可以通过上述用例,下面用例执行失败
用例2
输入:
MemSystem(100)
request(200)
预期输出:
null
-1
实际错误输出
null
0
在MemSystemRequest函数中增加下述代码,可以解决上述用例失败问题
if(sys->totalMemorySize < size)
{return -1;
}
执行用例,下述用例失败
用例3
MemSystem(100)
request(40)
request(30)
request(20)
request(10)
release(0)
release(40)
release(90)
request(70)
预期输出:
null
0
40
70
90
true
true
true
0
实际错误输出
null
0
40
70
90
true
true
true
-1
经过调试发现该行代码有问题,并修改可以解决上述用例失败问题。原因是应该是大于等于就可以申请内存。
if (sys->hashCount == 1) {if (sys->memoryUint[sys->hashMap[0].index].start > size) {
// 改成
if (sys->hashCount == 1) {if (sys->memoryUint[sys->hashMap[0].index].start >= size) {
下述用例失败
用例4
MemSystem(100)
request(40)
request(30)
request(20)
request(10)
release(0)
release(40)
release(90)
request(80)
release(70)
request(80)
release(0)
request(40)
request(60)
预期输出:
null
0
40
70
90
true
true
true
-1
true
0
true
0
40
实际错误输出
null
0
40
70
90
true
true
true
-1
true
0
true
0
-1
调试代码发现memoryUnit成员中的数据没有清空,可能会对后面的逻辑处理有影响,在MemSystemRelease函数中增加清空操作
if (sys->memoryUint[sys->hashMap[i].index].start == addr) {sys->hashMap[i].status = false;sys->hashMap[i].index = 0;
// 改成
if (sys->memoryUint[sys->hashMap[i].index].start == addr) {sys->memoryUint[sys->hashMap[sys->hashCount].index].start = 0;sys->memoryUint[sys->hashMap[sys->hashCount].index].end = 0;sys->hashMap[i].status = false;sys->hashMap[i].index = 0;
可以解决上述问题
执行代码下述测试用例错误
用例5
MemSystem(100)
request(10)
request(20)
request(30)
request(40)
release(30)
request(10)
request(10)
request(10)
// 预期输出
null
0
10
30
60
true
30
40
50
实际错误输出
null
0
10
30
60
true
10
30
40
调试代码发现MemoryUnit中的数据有的被清除了,检查代码发现刚才家的几行代码有问题。修改成下述形式可以解决这个问题
sys->memoryUint[sys->hashMap[sys->hashCount].index].start = 0;
sys->memoryUint[sys->hashMap[sys->hashCount].index].end = 0;
// 改成
sys->memoryUint[sys->hashMap[i].index].start = 0;
sys->memoryUint[sys->hashMap[i].index].end = 0;
再次执行代码成功
总结
未完待续
相关文章:
简易内存池(中)
提示:文章 文章目录 前言一、背景二、第二版代码用例2用例3用例4用例5 总结 前言 前期疑问: 本文目标: 一、背景 最近 二、 针对上述失败用例,修改代码如下 第二版代码 #include <stdbool.h> #include <stdio.h>…...
svn不能添加.a文件
解决办法 在home目录下有一个.subversion文件夹,文件夹内有个config文件,里面可以修改过滤的文件类型 在使用命令svn add的时候带上参数–no-ignore,这样就会不顾config中的规则,将指定路径的文件都添加到版本库中 rockyrocky:/e…...
PH47代码框架 24241231 重要更新
仪式感一下:2024年最后一天,发布 PH47 代码框架的一次重要更新。当然这并不是有意的,而是直到现在才把更新的所有工作全部做完(希望确实如此)。 本次更新要点: 1、加入多IMU支持。本次更新正式加入对 MPU65…...
小程序信息收集(小迪网络安全笔记~
免责声明:本文章仅用于交流学习,因文章内容而产生的任何违法&未授权行为,与文章作者无关!!! 附:完整笔记目录~ ps:本人小白,笔记均在个人理解基础上整理,…...
用户界面的UML建模07
4.2 抽象表示层的行为(Abstract Presentation Behaviour) AbstractForm 类定义了一组如下所示的四种操作: showForm() , getData() , sendConfirmation() 和sendCancellation()。在该阶段的设计过程(desig…...
LabVIEW手部运动机能实验系统
在运动科学、人机交互和康复训练等领域,手部运动功能的研究具有重要的应用价值。开发了一个基于LabVIEW的手部运动机能实验系统设计,该系统利用力量作为关键参数,通过实时数据采集和反馈帮助受试者完成精确的手部动作,同时为研究人…...
Java Map 源码解析:核心原理与应用
Java Map 源码解析:核心原理与应用 Java 的 Map 接口是集合框架中一个重要的组成部分,专门用于存储键值对。其强大的功能和灵活的实现使其在各种应用场景中得到了广泛的使用。本文面向对 Java 集合框架有一定了解的开发者,通过对 Map 接口及…...
基于Mosquito源码理解MQTT5.0的属性概念
MQTT 5.0协议相比之前的版本(如MQTT 3.1.1)增加了很多属性,这些属性分布于报文的可变头部(Variable Header)和有效载荷(Payload)中。这些属性大大增强了协议的可扩展性和灵活性,使其能够更好地适应现代物联网应用的复杂需求。 属性的定义在源码包mosquitto-2.0.18/inc…...
easyui textbox使用placeholder无效
easyui textbox使用placeholder无效 在easyui 的textbox控件,请使用data-options 设定 示例 <input type text class easyui-textbox data-options "prompt:请输入您的邮箱"/>...
java AQS
什么是AQS AQS(AbstractQueuedSynchronizer,抽象队列同步器)是 Java 中并发控制的一种机制,位于 java.util.concurrent.locks 包下,它为构建锁、信号量等同步工具提供了一个框架。AQS 通过 队列 来管理多个线程之间的…...
机器人对物体重定向操作的发展简述
物体重定向操作的发展简述 前言1、手内重定向和外部重定向2、重定向原语3、重定向状态转换网络4、连续任意姿态的重定向5、利用其他环境约束重定向总结Reference 前言 对于一些特殊的任务(如装配和打包),对物体放置的位姿由明确的要求&#…...
数据结构与算法之动态规划: LeetCode 72. 编辑距离 (Ts版)
编辑距离 https://leetcode.cn/problems/edit-distance/description/ 描述 给你两个单词 word1 和 word2, 请返回将 word1 转换成 word2 所使用的最少操作数你可以对一个单词进行如下三种操作: 插入一个字符删除一个字符替换一个字符 示例 1 输入&…...
vue3 Teleport瞬移组件
Teleport是瞬移组件,也称为传送门组件 它是一个可以使元素从一个组件转到另一个组件的组件。 如对话框、自定义菜单、警告提示、徽章,以及许多其他需要出现在特殊位置的自定义UI组件。假设现在页面中有两个元素,分别为div元素和button按钮元…...
Go语言学习路线
以下是一个较为系统的Go语言学习路线: 一、基础阶段 环境搭建与工具链熟悉 安装Go语言开发环境。在Go官方网站(https://golang.org/dl/)下载适合您操作系统的安装包并完成安装。 配置Go环境变量,如GOPATH和GOROOT。GOROOT是Go语…...
摄像头监视脚本
摄像头监视脚本,若检测到摄像头画面有变化,保存这一段视频 一、使用方法 1.运行脚本 默认参数Threshold3, Period3, path./recordings python cam.py --threshold30 --period3 --path./recordings 2.参数说明 threshold:摄像头捕获到的画面变化量阈值…...
【Leecode】Leecode刷题之路第97天之交错字符串
题目出处 97-交错字符串-题目出处 题目描述 个人解法 思路: todo代码示例:(Java) todo复杂度分析 todo官方解法 97-交错字符串-官方解法 方法1:动态规划 思路: class Solution {public boolean isInte…...
MAC环境安装(卸载)软件
MAC环境安装(卸载)软件 jdknode安装node,并实现不同版本的切换背景 卸载node从node官网下载pkg安装的node卸载用 homebrew 安装的node如果你感觉删的不够干净,可以再细分删除验证删除结果 jdk 1.下载jdk 先去官网下载自己需要的版…...
Spring Boot + Redisson 封装分布式锁
目标:一行代码调用,简单粗暴。 基操:自动加锁,自动解锁,自动处理异常,自动处理锁超时等。 安装 redis redisson <dependency><groupId>org.springframework.boot</groupId><artifac…...
从零开发一套UWB定位系统需要多长时间?UWB超宽带定位系统源码
从零开发一套UWB定位系统需要多长时间? 从零开发一套UWB定位系统所需的时间会受到多种因素的影响,以下是详细分析: 一、系统复杂度 1、基本功能定位系统 如果只是开发一个简单的UWB定位系统,仅实现基本的定位功能,如在…...
DataCap 2024.4.1 版本发布:MongoDB 驱动支持、工作流引擎升级
尊敬的 DataCap 用户: DataCap 2024.4.1 版本现已正式发布。本次更新包含多项重要功能升级和性能优化,现将主要更新内容公布如下: 核心功能升级 数据库功能增强 (实现功能) 新增数据库管理功能:支持创建、删除和切换数据库完善表…...
常见端口(22、25、53、80、443、110、143、3306、6379、21)和服务的安装与配置手册
文章目录 一、系统初始设置1. 系统与工具的基础配置1.1 系统更新1.2 网络连接测试1.3 工具安装 2. 防火墙配置2.1 启用防火墙服务2.2 检查默认规则2.3 开放常用端口2.4 查看已开放端口 二、常见端口及其用途1. 端口 22(SSH)2. 端口 25(SMTP&a…...
使用maven-mvnd替换maven大大提升编译打包速度
先上结论!!! 多模块清理并打包提升:约3.5倍 多模块不清理打包提升:约5.5倍 单模块提升:约2倍 从计算结果来看,多模块提升的效率更高。在使用mvnd package打包多模块式,可在控制台…...
图像去雾 | 基于Matlab的图像去雾系统(四种方法)
图像去雾 | 基于Matlab的图像去雾系统(四种方法) 目录 图像去雾 | 基于Matlab的图像去雾系统(四种方法)效果一览基本介绍程序设计参考资料 效果一览 基本介绍 基于Matlab的图像去雾系统(四种方法) 关于图像…...
【Ubuntu 系统 之 开启远程桌面SSH登录】
【Ubuntu 系统 之 开启远程桌面&SSH登录】 一、开启 SSH 登录二、开启远程桌面1、更新包管理器并安装 xrdp1.1、遇到错误1.2、解决方法 2、安装桌面环境(如果服务器上没有 GUI)3、配置 xrdp 使用默认的 GNOME 桌面环境4、配置防火墙允许远程桌面连接…...
利用 AI 生成 XMind 思维导图教程
本文将介绍如何使用 AI 工具(如 ChatGPT 等),从无到有生成层次分明、可直接导入到 XMind 的 Markdown 格式思维导图。主要步骤包括:选择主题、编写并润色 Markdown 文档、在 XMind 中进行导入与可视化。 一、为什么使用 AI XMind…...
电子应用设计方案81:智能AI冲奶瓶系统设计
智能 AI 冲奶瓶系统设计 一、引言 智能 AI 冲奶瓶系统旨在为父母或照顾者提供便捷、准确和卫生的冲奶服务,特别是在夜间或忙碌时,减轻负担并确保婴儿获得适宜的营养。 二、系统概述 1. 系统目标 - 精确调配奶粉和水的比例,满足不同年龄段婴…...
MySQL的索引
没有索引会怎么样 数据库中的数据最终是存储在磁盘上的。 mysql服务器,本质上是内存进程,CURD操作全都是在内存中进行的—索引也是如此。 所以,需要将数据从磁盘读进内存,才能进行操作。 如果没有索引,表中的数据会向…...
Pytest 高级用法:间接参数化
文章目录 1. 引言2. 基础概念2.1 Fixture2.2 参数化 3. 代码实例3.1 基础设置3.2 测试用例示例示例 1:基础的间接参数化示例 2:通过 request 获取参数值示例 3:多参数组合测试示例 4:部分间接参数化 4. 最佳实践5. 总结参考资料 1…...
基于视觉语言模型(VLM)的CogAgent
前言 CogAgent 是由清华大学与智谱AI联合推出的一个多模态大模型,专注于图形用户界面(GUI)的理解和导航。它代表了在视觉语言模型(VLM)领域的一项重要进展,特别是在GUI Agent能力方面。相较于传统的基于文…...
文件传输工具FTransferor<优化篇>
在上一篇文章中,我们详细探讨了FTransferor文件传输工具的设计与实现,并展示了它在局域网文件传输方面的高效性。然而,随着互联网应用场景的不断丰富,传统的基于 TCP/UDP 的传输方式已经无法满足部分开发者的需求。特别是在跨平台…...
【Linux】Centos7下载npm
Index of /dist/v16.20.2/ (nodejs.org) 下载 wget https://nodejs.org/dist/v16.20.2/node-v16.20.2-linux-x64.tar.gz解压 sudo tar -zxvf node-v16.20.2-linux-x64.tar.gz 配置环境变量 sudo vim /etc/profile export NODE_HOME/usr/local/node-v16.20.2-linux-x64 ex…...
Spring boot + Hibernate + MySQL实现用户管理示例
安装MySQL Windows 11 Mysql 安装及常用命令_windows11 mysql-CSDN博客 整体目录 pom.xml <?xml version"1.0" encoding"UTF-8"?> <project xmlns"http://maven.apache.org/POM/4.0.0" xmlns:xsi"http://www.w3.org/2001/XMLS…...
Neo4j GDS 2.0 安装与配置
Neo4j GDS 2.0 安装与配置 GDS插件安装:Neo4j官方文档 1. GDS简介 Neo4j Graph Data Science (GDS) 库作为 Neo4j Graph Database 的插件提供。该插件需要安装到数据库中并在 Neo4j 配置中列入白名单。有两种主要方法可以实现这一点,我们将在本章中详…...
【非关系型数据库Redis 】 入门
Redis入门 一、非关系型数据库概述 (一)概念 非关系型数据库(NoSQL,Not Only SQL)是相对于传统的关系型数据库而言的一种数据存储管理系统。它摒弃了关系型数据库中严格的表结构、SQL 语言操作以及复杂的事务等特性…...
【Linux报告】实训一:GNME桌面环境的设置及应用
实训一:GNME桌面环境的设置及应用 【练习1】在图形模式和文本模式下登录Linux系统。 1、开启Linux虚拟机。 答:打开此虚拟机如图所示 2、观察屏幕上显示的启动信息。 3、当系统启动到图形界面时,用普通用户身份登录。 答:如图…...
mysql8 从C++源码角度看 客户端发送的sql信息 mysql服务端从网络读取到buff缓存中
MySQL 8 版本中的客户端-服务器通信相关,特别是在接收和解析网络请求的数据包时。以下是对代码各个部分的详细解释,帮助您更好地理解这些代码的作用。 代码概述 这段代码主要负责从网络读取数据包,它包含了多个函数来处理网络数据的读取、缓…...
log4j2的Strategy、log4j2的DefaultRolloverStrategy、删除过期文件
文章目录 一、DefaultRolloverStrategy1.1、DefaultRolloverStrategy节点1.1.1、filePattern属性1.1.2、DefaultRolloverStrategy删除原理 1.2、Delete节点1.2.1、maxDepth属性 二、知识扩展2.1、DefaultRolloverStrategy与Delete会冲突吗?2.1.1、场景一:…...
macos 支持外接高分辩率显示器开源控制软件
macos 支持外接高分辩率显示器开源控制软件 软件(app应用)名:BetterDisplay 官方地址: https://github.com/waydabber/BetterDisplay...
HTML5实现好看的喜庆圣诞节网站源码
HTML5实现好看的喜庆圣诞节网站源码 前言一、设计来源1.1 主界面1.2 圣诞介绍界面1.3 圣诞象征界面1.4 圣诞活动界面1.5 圣诞热度界面1.6 圣诞纪念界面1.7 联系我们界面 二、效果和源码2.1 动态效果2.2 源代码 源码下载结束语 HTML5实现好看的喜庆圣诞节网站源码,圣…...
鸿蒙 NEXT 开发中,使用公共事件进行进程间通信
大家好,我是 V 哥,在鸿蒙 NEXT 开发中,使用公共事件进行进程间通信(IPC)是一种常见的做法。下面我将提供一个完整的业务代码示例,并解释逻辑关系,以便即使是初学者也能按照步骤进行实操…...
算法-excel表头位置转成对应数字 26进制转10进制
给你一个字符串 columnTitle ,表示 Excel 表格中的列名称。返回 该列名称对应的列序号 。 例如: A -> 1 B -> 2 C -> 3 ... Z -> 26 AA -> 27 AB -> 28 ... 示例 1: 输入: columnTitle "A" 输出: 1示例 2: 输入: colu…...
清华发布Hyper-YOLO:超图计算+目标检测!捕捉高阶视觉关联
目录 论文信息 引言 背景 算法概括 超图计算 Hyper-YOLO整体架构 基于超图的跨层次和跨位置表示网络 Coovally AI模型训练与应用平台 实验结论 总结 论文信息 题目:Hyper-YOLO: When Visual Object Detection Meets Hypergraph Computation Hyper-YOLO&a…...
如何使用网络工具进行网络性能评估
网络评估是对IT基础设施的系统评估,以确保它能够很好地满足企业的核心运营需求,确定了基础设施中需要改进的领域,并定义了改进的范围。 网络评估工具分析IT基础设施的各个方面,它通过评估网络设备、网络性能和安全威胁来仔细检查…...
MyBatis执行一条sql语句的流程(源码解析)
提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 MyBatis执行一条sql语句的流程(源码解析) MyBatis执行sql语句的流程加载配置文件加载配置文件的流程 创建sqlsessionFactory对象解析Mapper创建sqlses…...
使用three.js 实现vr全景图展示,复制即可用
1.实现效果 2.代码 1.npm安装three.js npm install three 2.引入three.js import * as THREE from three import { OrbitControls } from three/examples/jsm/controls/OrbitControls 3.初始化模型 init(val) {this.container document.querySelector(.container)// 初始…...
MATLAB关于集合的运算(部分)
集合运算比较两个集合中的元素,以找出共性或差异 i n t e r s e c t intersect intersect表示两组数据的交集 i s m e m b e r ismember ismember表示查找数据的集合成员 u n i o n union union表示两个数据集的并集 u n i q u e unique unique表示查找数据集的…...
谈谈数据产品开发流程
数据产品开发流程涵盖以下关键步骤:首先是需求调研与规划,通过与业务部门等沟通,明确产品定位、受众及功能,制定项目计划。接着进行数据采集与处理,确定数据源,运用合适工具采集并清洗、转换数据后存储。然…...
Unity3D仿星露谷物语开发12之创建道具列表
1、目标 道具是游戏的核心部分,道具包括你可以拾取的东西,你可以使用的工具和你能种的东西等。 本节就是创建道具的信息类。同时了解ScriptableObject类的使用。 2、创建道具枚举类 修改Assets -> Scripts -> Enums.cs脚本, 新增如…...
Linux(Centos 7.6)常见基础配置
1.网络配置 网络配置详见:VMware安装Linux(Centos 7.6)后网络配置 2.yum源配置 yum源配置详见:Linux(Centos 7.6)yum源配置 3.主机名配置 1.Linux(Centos 7.6)系统安装后,没有配置主机名时,root用户登录后,是如下…...
2024年底关于期货的工作总结
十几年程序猿出身,因几年前的懵懂无畏闯入期货市场,盈了,感觉期货太简单,飘然裸辞,想当财务自由者,全职做交易。当深入学习时,却亏了,原来市场是让人敬畏的,也是反人性的…...