C++动态内存的管理

今天来分享C++动态内存管理相关知识,闲言勿谈,直接上干货。

1. 动态内存的开辟和销毁(new和delete)

(1)前置知识:我们知道c语言有malloc和calloc和realloc三个函数可以进行动态的开辟内存,那么它们有什么区别呢?首先是malloc,malloc表示直接在堆上动态开辟内存空间,返回void*,而calloc不仅可以直接在堆上动态开辟内存空间,还会把开辟空间的内容初始化为0,calloc返回的也是void*,realloc是在原有的空间的基础上进行扩容,也是返回void*.c语言虽然有三个动态开辟内存的函数,但在某些场景下不适用,同时用起来也比较麻烦,所以c++引入了一个new操作符进行动态开辟内存,delete操作符进行销毁开辟的内存,那么接下来我们看看new的用法吧。

(2)new和delete用法

new和delete操作符对内置类型进行开辟空间

new和malloc对于内置类型开辟空间,功能都差不多。

cpp 复制代码
int main()
{
	//表示在堆上申请一个int空间
	int* p1 = new int;
	delete p1;

	//表示在堆上申请一个int空间并初始化为4
	int* p2 = new int(4);
	delete p2;

	//表示在堆上申请3个int空间
	int* p3 = new int[3];
	delete[] p3;

	return 0;
}

new和delete操作符对自定义类型进行开辟空间

我们来看看new和malloc对于自定义类型开辟空间的不同之处。

cpp 复制代码
class A
{
public:
	A(int a = 0)
		: _a(a)
	{
		cout << "A():" << this << endl;
	}
	~A()
	{
		cout << "~A():" << this << endl;
	}
private:
	int _a;
};

int main()
{
	A* p1 = (A*)malloc(sizeof(A));

	A* p2 = new A;

	free(p1);
	delete p2;
	return 0;
}

我们来看看这个代码运行的结果

咋出现了调用构造函数和析构函数呢?是谁调用的呢?

我们把malloc和free的函数进行注释掉,如果还调用构造函数和析构函数,那么证明是new和delete调用的构造函数和析构函数。

cpp 复制代码
class A
{
public:
	A(int a = 0)
		: _a(a)
	{
		cout << "A():" << this << endl;
	}
	~A()
	{
		cout << "~A():" << this << endl;
	}
private:
	int _a;
};

int main()
{
	/*A* p1 = (A*)malloc(sizeof(A));*/

	A* p2 = new A;

	//free(p1);
	delete p2;
	return 0;
}

还是调用了构造函数和析构函数,现在我们就清楚了malloc函数和new操作符,free函数和delete操作符之间的区别是,new开辟空间是会调用构造函数进行初始化,delete在释放空间是会调用析构函数对对象中的资源进行清理。

(2)operator new函数和operator delete函数

我们先来看看c++标准库里面是如何实现operator new和operator delete函数的。

我们可以看到operator new和operator delete是依靠malloc和free函数实现的,该函数实际通过malloc来申请空间,当malloc申请空间成功时直接返回;申请空间失败,尝试执行空间不足应对措施,如果改应对措施用户设置了,则继续申请,否则抛异常。

new和delete实现的原理

(1)对于内置类型,new和malloc功能相似,delete和free功能相似。

(1)对于自定义类型

new不仅调用operator new函数开辟空间还会调用构造函数。

delete不仅会调用operator delete函数释放空间,还会调用析构函数完成对对象资源的清理工作

总结:

1.共同点:malloc和new都是在堆上开辟空间,都需要手动释放开辟的空间

2.不同点:malloc和free是函数,new和delete是操作符(概念性质不同)

malloc开辟空间是要传需要开辟的字节数,返回的是void*;而new后跟申请对象的类型,返回的是申

请对象的类型的指针

new会调用构造函数,开辟失败会抛异常,malloc开辟失败会返回0

相关推荐
艾莉丝努力练剑3 分钟前
【AI大模型接入SDK】Gemini模型接入知识体系
java·开发语言·网络·人工智能·网络协议·学习·http
传奇开心果编程7 分钟前
【Rust入门知识点学与练】第13课:枚举 Enum
开发语言·学习·rust
一木 之林10 分钟前
四、STL 容器与数据结构(进阶)(二)
数据结构·c++·哈希算法
zhanghaha131412 分钟前
Python进阶教程:28_queue 队列模块 零基础超详细教程
java·开发语言·python
司小豆17 分钟前
第七课:DeepSeek Harness 服务与依赖注入
java·服务器·开发语言·github·ai编程
会周易的程序员20 分钟前
5Draft使用说明书
服务器·c++·分布式·raft·共识
ysu_031426 分钟前
02-单链表完全指南
c语言·数据结构·算法·leetcode
weixin1997010801629 分钟前
[特殊字符]《闲鱼 + 淘宝 + 1688 三平台库存同源:二手ERP主数据治理与超卖防御》(附Python源码)
开发语言·python
ltqshs34 分钟前
C语言-链表例程
c语言·开发语言·链表
码匠许师傅35 分钟前
【设计模式精讲】21.迭代器模式(Iterator)
c++·设计模式·rpc·迭代器模式·软件工程·uml