【小梦C嘎嘎——启航篇】内存管理小知识~
【小梦C嘎嘎——启航篇】内存管理小知识~😎
- 前言🙌
- malloc/calloc/realloc的区别?
- new 与 delete
- new与delete要找好搭档才能保证万无一失
- new 与 delete的内部实现细节是怎么样的呢???
- new 的内部实现细节
- delete的内部实现细节
- 经典问题:malloc/free 与new/delete 的区别是什么???
- 抛异常的基本使用
- 小知识点:cout 流插入 不能打印出char*指针的地址
- 总结撒花💞
😎博客昵称:博客小梦
😊最喜欢的座右铭:全神贯注的上吧!!!
😊作者简介:一名热爱C/C++,算法等技术、喜爱运动、热爱K歌、敢于追梦的小博主!
😘博主小留言:哈喽!😄各位CSDN的uu们,我是你的博客好友小梦,希望我的文章可以给您带来一定的帮助,话不多说,文章推上!欢迎大家在评论区唠嗑指正,觉得好的话别忘了一键三连哦!😘
前言🙌
哈喽各位友友们😊,我今天又学到了很多有趣的知识,现在迫不及待的想和大家分享一下! 都是精华内容,可不要错过哟!!!😍😍😍
malloc/calloc/realloc的区别?
这是一个经典的问题,有时面试也会这么问你。我的理解是:malloc可以向堆区动态申请一段连续的空间,realloc 的话主要是完成扩容操作,其扩容又可以分为两种方式:1.原地扩容 ;2.异地扩容。异地扩容的代价比较高,因为它要在堆区去找一块能够满足需求的空间,然后将原来的数据内容拷贝到新申请的空间里面,然后再把原来申请的空间释放掉。而calloc的话就是在malloc的基础上,能够将自己申请的空间进行初始化操作。以上就是他们三者的区别与联系啦~
new 与 delete
在C语言中我们知道有malloc ,realloc,calloc 这些可以在堆区中申请资源,可以用free释放掉堆上开辟的空间。那为什么C++还自己搞一套呢???不要问,C嘎嘎祖师爷那么设计一定有他的道理!!!接下来,我就来分析一下为什么。
new与delete要找好搭档才能保证万无一失
由于我们场景需求的多样,因此new与delete产生了不同的搭档方式以满足我们的需求。简单概括为:
- 一个变量空间的申请与释放:new 变量类型(val) <-----> delete 变量名
- 一个变量空间的申请与释放:new 变量类型【变量个数】(val) <-----> delete【】 变量名
#include<iostream>
using namespace std;class A
{
public:A(int a = 0):_a(a){cout << "A(int a = 0)" << endl;}~A(){cout << "~A()" << endl;}
private:int _a;
};int main()
{int* a = new int(10);cout << *a << endl;delete a;A* ptr1 = new A[10];delete[] ptr1;return 0;
}

new与delete要找好搭档才能保证万无一失,如果随意搭档可能会出错的。例如下面这个场景就会导致运行错误。
class A
{
public:A(int a = 0):_a(a){cout << "A(int a = 0)" << endl;}~A(){cout << "~A()" << endl;}
private:int _a;
};int main()
{int* a = new int(10);cout << *a << endl;A* ptr1 = new A[10];delete ptr1;//delete[] ptr1;return 0;
}

因此,我们在使用的时候,一定要根据场景的需求去选择new 与 delete 的 匹配搭档。
new 与 delete的内部实现细节是怎么样的呢???
new 的内部实现细节
其实new 之所以可以申请空间并且完成初始化操作,其实其内部是调用了 malloc 和 构造函数来实现的。那它们又是怎么调用malloc和构造的呢?内部实现的细节是怎么样的? 其实这里使用了封装的方法,其内部实现是写了一个operator new函数,这个函数里面封装了malloc函数的调用以及抛异常的实现。因此,operator new函数就完成了new的开空间和如果new失败了会抛异常的功能。然后调用new,编译器会自动调用构造函数进行对象的初始化操作。
delete的内部实现细节
其实delete之所以可以释放空间并且完成对象资源清理的工作,其实其内部是调用了free函数 和 析构函数来实现的。那它们又是怎么调用free函数 和 析构函数的呢?内部实现的细节是怎么样的? 其实这里也使用了封装的方法,其内部实现是写了一个operator delete函数,这个函数里面封装了free函数的调用。因此,operator delete函数就完成了对象资源的释放。然后调用delete,编译器会自动调用析构函数进行对象空间的释放。
从他们内部实现的细节可以看出,如果只是对内置类型变量,那么使用malloc + free 与使用 new + delete 都可以完成空间的开辟和释放。但是,对于自定义类型就只能用new+delete。最主要的原因就是:new和delete会自动调用构造函数和析构函数,而malloc和free不能。
经典问题:malloc/free 与new/delete 的区别是什么???
我的理解是:
-
从语法角度上看:
malloc ,free是函数,而new与delete是操作符。malloc需要自己手动计算所要申请空间的大小而new直接加类型然后在后面【】里面写上对象个数即可。malloc 返回的是vold*指针需要强转,而new不用,返回的就是该对象类型的指针。malloc开辟失败是会返回NULL,我们需要自己写一个检查代码来判断是否开辟失败,而new开辟失败会抛出异常,无需我们写检查代码。malloc只能完成申请空间的功能,而new既可以申请空间又可以进行初始化。
-
从底层原理实现的角度上看:
申请自定义类型对象时,malloc/free只会开辟空间,不会调用构造函数与析构函数,而new
在申请空间后会调用构造函数完成对象的初始化,delete在释放空间前会调用析构函数完成
空间中资源的清理
抛异常的基本使用
C++中的new有抛异常的功能。而try()catch()则可以去捕获new抛出的异常。
首先需要将要检查的代码放在try()里面,或者在这里面进行调用,才能够对该代码段进行异常的检查和捕获。一旦捕获到异常,就会自动跳转到catch()里面,然后进行异常的处理。下面是一个在32位平台上的应用举例:
void func()
{char* p1 = new char[0x7fffffff];cout << (void*)p1 << endl;cout << "hello world" << endl;
}int main()
{try{func();}catch (const exception& e){cout << e.what() << endl;}return 0;
}
运行结果截图:

小知识点:cout 流插入 不能打印出char*指针的地址
原因:cout 会自动识别其为字符串,并按照字符串的格式进行打印,遇到"/0"就会结束打印。
解决方案:将其强转为其他类型即可解决。
错误代码:

程序运行结果:

修改后的代码:

运行结果:

总结撒花💞
希望大家通过阅读此文有所收获!
😘如果我写的有什么不好之处,请在文章下方给出你宝贵的意见😊。如果觉得我写的好的话请点个赞赞和关注哦~😘😘😘
相关文章:
【小梦C嘎嘎——启航篇】内存管理小知识~
【小梦C嘎嘎——启航篇】内存管理小知识~😎 前言🙌malloc/calloc/realloc的区别?new 与 deletenew与delete要找好搭档才能保证万无一失 new 与 delete的内部实现细节是怎么样的呢???new 的内部实现细节dele…...
ClickHouse查看执行计划(EXPLAIN语法)
1.EXPLAIN 语法示例 EXPLAIN [AST | SYNTAX | QUERY TREE | PLAN | PIPELINE | ESTIMATE | TABLE OVERRIDE] [setting value, ...] [ SELECT ... | tableFunction(...) [COLUMNS (...)] [ORDER BY ...] [PARTITION BY ...] [PRIMARY KEY] [SAMPLE BY ...] [T…...
线程池
线程池 什么是线程池? 想象一下 假设我是个漂亮妹子,这时候接受了舔狗A的表白,随着时间的推移,逐渐不喜欢A这小子了,于是我就想换个男朋友,可是 1.处理分手,需要消耗一定成本 2.再找一个新对象…...
配置:Terminal和oh-my-posh
目录 命令行安装oh-my-posh查看安装情况配置PowerShell启用oh-my-posh、设置主题配色安装字体Terminal中的配置 命令行安装oh-my-posh Set-ExecutionPolicy Bypass -Scope Process -Force; Invoke-Expression ((New-Object System.Net.WebClient).DownloadString(https://ohmy…...
数据结构--BFS求最短路
数据结构–BFS求最短路 BFS求⽆权图的单源最短路径 注:⽆权图可以视为⼀种特殊的带权图,只是每条边的权值都为1 以 2 为 b e g i n 位置 以2为begin位置 以2为begin位置 代码实现 //求顶点u到其他顶点的最短路径 void BFS_MIN_Distance(Graph G, int u…...
FPGA应用学习笔记----定点除法的gold算法流水线设计
猜一个Y0 a和b上下都Y0 分母越接近一,分子就越接近答案 误差: 下一步迭代为 Y的迭代值: 误差值: 代码的实现如上所示...
Nginx转发的原理和负载均衡
一、Nginx转发的原理 Nginx是一个高性能的反向代理服务器,它可以用于实现请求的转发和负载均衡。以下是Nginx转发的基本原理: 客户端发送请求:客户端向Nginx服务器发送HTTP请求。 Nginx接收请求:Nginx服务器接收到客户端的请求。…...
怎么换ip地址 电脑切换ip地址方法
互联网时代,IP地址是我们在网络上进行通信和访问的身份标识。有时候,我们可能需要更改IP地址,以便获得更好的网络体验或绕过某些限制。本文将介绍如何使用深度IP转换器来更改IP地址。 1:了解IP地址 IP地址是一个由数字和点组成的标…...
软件设计基础
巩固基础,砥砺前行 。 只有不断重复,才能做到超越自己。 能坚持把简单的事情做到极致,也是不容易的。 软件项目管理。 在经历了软件危机和大连的软件项目失败以后,人们对软件工程专业的现状进行了多次分析。得出了普遍性的结论&…...
OptaPlanner笔记5
2.4 与spring boot集成 2.4.4 添加依赖 <dependency><groupId>org.optaplanner</groupId><artifactId>optaplanner-spring-boot-starter</artifactId> </dependency>2.4.8 创建求解器服务 import org.optaplanner.core.api.solver.Solv…...
PS注意事项优漫动游
PS入门注意事项AdobePhotoshop是目前最流行的平面设计软件之一。可以说,只要你接触平面设计,那么无论早晚,你都要和它打交道。关于Photoshop,要说的实在太多太多,但不论你想让它成为你的左膀右臂,或者仅仅是…...
matplotlib 判断鼠标是否点击在当前线上
在开发中有一个需求:对生成的一条线进行拖拽。 我将这个方法实现在线所在的类里,这个过程中需要判断鼠标是否点击在当前线上,从而实现拖拽。 实现代码如下: # 点击事件 def on_press(self,event):if event.inaxes ! self.ax:retur…...
bash中(冒号破折号)的用法 —— 筑梦之路
${PUBLIC_INTERFACE:-eth0} :- 的用途是什么? 含义:如果 $PUBLIC_INTERFACE 存在且不是 null,则返回其值,否则返回 "eth0"。 ${parameter:-word} 使用默认值。如果 parameter 未设置或为 null,则 word 的扩…...
LeetCode150道面试经典题--同构字符串(简单)
1.题目 给定两个字符串 s 和 t ,判断它们是否是同构的。如果 s 中的字符可以按某种映射关系替换得到 t ,那么这两个字符串是同构的。每个出现的字符都应当映射到另一个字符,同时不改变字符的顺序。不同字符不能映射到同一个字符上,…...
Redis - 数据类型映射底层结构
简介 从数据类型上体现就是,同一个数据类型,在不同的情况下会使用不同的编码类型,底层所使用的的数据结构也不相同。 字符串对象 字符串对象的编码可以是 int、raw 和 embstr 三者之一。 embstr 编码是专门用于保存简短字符串的一种优化编…...
MySQL数据库表的增删查改 - 进阶
一,数据库约束 1.1 约束对象 not null - 该列不能为空unique - 保证该列的每一行都不一样default - 规定没有给列赋值时的默认值(自定义)primary key - not null 和 unique 的结合,会给该列添加一个索引࿰…...
8086汇编语言工作环境 百度网盘下载
链接:https://pan.baidu.com/s/1-1K7gX859xejaUK70OTgtw?pwdbfa5 提取码:bfa5 为了方便下载,找了很多资料,也是从其他人那边分享过来的,也方便其他人 文件内容:...
ES6 解构
解构的语法 … {} 解构的语法中,...(展开运算符)和 {}(对象字面量)扮演着不同的角色。 ...(展开运算符): 在解构中,... 被用作展开运算符,用于将数组或对象中…...
React三个状态时触发的相应钩子
01.初始化状态。 这个阶段由render()函数触发; 1.constructor(); 2.componentWillMount(); 在17版本以后改为UNSAFE_componentWillMount() reason:react为组件异步渲染做准备; 3.render(); 4.componentDidMount(); 这…...
阿里云服务器部署Drupal网站教程基于CentOS系统
阿里云百科分享如何在CentOS 7操作系统的ECS实例上搭建Drupal电子商务网站。Drupal是使用PHP语言编写的开源内容管理框架(CMF),它由内容管理系统(CMS)和PHP开发框架(Framework)共同构成。它用于…...
TDengine 快速体验(Docker 镜像方式)
简介 TDengine 可以通过安装包、Docker 镜像 及云服务快速体验 TDengine 的功能,本节首先介绍如何通过 Docker 快速体验 TDengine,然后介绍如何在 Docker 环境下体验 TDengine 的写入和查询功能。如果你不熟悉 Docker,请使用 安装包的方式快…...
微信小程序之bind和catch
这两个呢,都是绑定事件用的,具体使用有些小区别。 官方文档: 事件冒泡处理不同 bind:绑定的事件会向上冒泡,即触发当前组件的事件后,还会继续触发父组件的相同事件。例如,有一个子视图绑定了b…...
51c自动驾驶~合集58
我自己的原文哦~ https://blog.51cto.com/whaosoft/13967107 #CCA-Attention 全局池化局部保留,CCA-Attention为LLM长文本建模带来突破性进展 琶洲实验室、华南理工大学联合推出关键上下文感知注意力机制(CCA-Attention),…...
【ROS】Nav2源码之nav2_behavior_tree-行为树节点列表
1、行为树节点分类 在 Nav2(Navigation2)的行为树框架中,行为树节点插件按照功能分为 Action(动作节点)、Condition(条件节点)、Control(控制节点) 和 Decorator(装饰节点) 四类。 1.1 动作节点 Action 执行具体的机器人操作或任务,直接与硬件、传感器或外部系统…...
C++ 基础特性深度解析
目录 引言 一、命名空间(namespace) C 中的命名空间 与 C 语言的对比 二、缺省参数 C 中的缺省参数 与 C 语言的对比 三、引用(reference) C 中的引用 与 C 语言的对比 四、inline(内联函数…...
【配置 YOLOX 用于按目录分类的图片数据集】
现在的图标点选越来越多,如何一步解决,采用 YOLOX 目标检测模式则可以轻松解决 要在 YOLOX 中使用按目录分类的图片数据集(每个目录代表一个类别,目录下是该类别的所有图片),你需要进行以下配置步骤&#x…...
Caliper 配置文件解析:config.yaml
Caliper 是一个区块链性能基准测试工具,用于评估不同区块链平台的性能。下面我将详细解释你提供的 fisco-bcos.json 文件结构,并说明它与 config.yaml 文件的关系。 fisco-bcos.json 文件解析 这个文件是针对 FISCO-BCOS 区块链网络的 Caliper 配置文件,主要包含以下几个部…...
【JavaWeb】Docker项目部署
引言 之前学习了Linux操作系统的常见命令,在Linux上安装软件,以及如何在Linux上部署一个单体项目,大多数同学都会有相同的感受,那就是麻烦。 核心体现在三点: 命令太多了,记不住 软件安装包名字复杂&…...
Android Bitmap治理全解析:从加载优化到泄漏防控的全生命周期管理
引言 Bitmap(位图)是Android应用内存占用的“头号杀手”。一张1080P(1920x1080)的图片以ARGB_8888格式加载时,内存占用高达8MB(192010804字节)。据统计,超过60%的应用OOM崩溃与Bitm…...
微软PowerBI考试 PL300-在 Power BI 中清理、转换和加载数据
微软PowerBI考试 PL300-在 Power BI 中清理、转换和加载数据 Power Query 具有大量专门帮助您清理和准备数据以供分析的功能。 您将了解如何简化复杂模型、更改数据类型、重命名对象和透视数据。 您还将了解如何分析列,以便知晓哪些列包含有价值的数据,…...

