【C++笔记】内存管理流食般投喂

声明:以下知识相关资料来自比特官网和小编手搓~
C/C++内存管理

++1、C/C++内存分布++

++2、C语言中动态内存管理方式:malloc/calloc/realloc/free++

++3、C++内存管理方式++

3.1、new/delete操作内置类型

3.2、new和delete操作自定义类型

++4、operator new 与 operator delete 函数++

++5、new 和 delete 的实现原理++

5.1、内置类型

5.2、自定义类型

++6、定位new表达式(placement-new)++

++7、malloc/free 和 new/delete 的区别++

1、C/C++内存分布

C语言和C++的内存划分是一样的,常见内存区域就是:栈区、堆区、静态区、常量区,现在推出命名更加官方的区域划分:静态区 -> 数据段;常量区 -> 代码段。

栈区:函数栈帧的创建,其空间就是在栈上申请的,常见的局部变量也在这,及时申请、销毁,还有函数参数、返回值等等。

堆区:当数据结构存储数据空间不够时,额外申请的空间都是在堆区上申请开辟的,这个区域是给操作者发挥的区域。

给点题目试试水:

cpp 复制代码
int globalVar = 1;
static int staticGlobalVar = 1;
void Test()
{
    static int staticVar = 1;
    int localVar = 1;

    int num1[10] = { 1, 2, 3, 4 };
    char char2[] = "abcd";
    const char* pChar3 = "abcd";
    int* ptr1 = (int*)malloc(sizeof(int) * 4);
    int* ptr2 = (int*)calloc(4, sizeof(int));
    int* ptr3 = (int*)realloc(ptr2, sizeof(int) * 4);
    free(ptr1);
    free(ptr3);
}

2、C语言中动态内存管理方式:malloc/calloc/realloc/free

*3、*C++内存管理方式

C++这里用独有的 new 和 delete 操作符进行内存管理。

3.1、new/delete操作内置类型

cpp 复制代码
void Test()
{
    // 动态申请一个int类型的空间
    int* ptr4 = new int;
    
    // 动态申请一个int类型的空间并初始化为10
    int* ptr5 = new int(10);

    // 动态申请10个int类型的空间
    int* ptr6 = new int[10];

    delete ptr4;
    delete ptr5;
    delete[] ptr6; //格式一一对应
}

注意:申请&释放一个空间 -> new & delete;

申请&释放连续的空间 -> new\[\] & delete\[\]。

3.2、new和delete操作自定义类型

new/delete 和 malloc/free 的最大区别,就是 new/delete 除了会开空间,还会调用构造函数/析构函数。

cpp 复制代码
//现有一个 A类

int main()
{
    A* p1 = (A*)malloc(sizeof(A));
    A* p2 = new A(1);    
    free(p1);
    delete p2;

    A* p3 = (A*)malloc(sizeof(A) * 10);
    A* p4 = new A[10];
    free(p3);
    delete[] p4;

    return 0;
}

4、operator new 与 operator delete 函数

operator new 其实就是malloc的套个公司换个名的事,不过operator new解决了malloc申请完要手动验证是否申请成功,operator new是不需要管的,他自己会处理,申请失败了会抛异常。

operator delete同理也就是free套个公司换个名的事。

5、new 和 delete 的实现原理

5.1、内置类型

内置类型对于new/delete 与 malloc/free来说,基本是一样的,只不过对于单个空间和连续空间,用的是 new/delete 和 new\[\]/delete\[\];对于空间申请失败,new是抛异常,malloc是返回NULL。

5.2、自定义类型

new 的原理:

调用operator new函数申请空间,再调用构造函数对申请的空间进行构造。

底层:malloc + 构造

delete 的原理:

先调用析构函数,对申请的资源进行清理与释放。

底层:析构 + free

new TN 的原理:

调用operator new\[\]函数,实际是调用operator new函数申请N个对象空间;在申请的空间上进行N次构造函数的执行。

delete\[\] 的原理:

先调用N次析构函数,对N个对象申请的资源进行清理和释放;再调用operator delete\[\]函数,实际调用operator delete函数释放空间。

6、定位new表达式(placement-new)

定位new表达式的使用场景是配合着内存池进行使用的。内存池:生活费小金库,妈妈每月定期给我、爸爸、姐姐生活费,我们日常开销就在自己的生活费小金库里面取,不需要有一笔消费。就问妈妈要。放在内存池里面的空间只是有一些空间放那,我们可以找他要空间,但是对于自定义类型对象,要来空间的并没有调用构造函数进行初始化,这个工作就交给了 定位new表达式。

定位new表达式的使用方法:new(指针,指向空间)类型 / new(指针,指向空间)类型(实参,初始化值)

cpp 复制代码
int main()
{
    A* p1 = (A*)malloc(sizeof(A));
    new(p1)A;
    p1->~A(); // 成员函数并不包含在对象里,但是得通过对象去公共存储池里去调用
    free(p1);

    A* p2 = (A*)malloc(sizeof(A));
    new(p2)A(10);
    p2->~A();
    free(p2);

    return 0;
}

7、malloc/free 和 new/delete 的区别

相同点:在堆上申请空间,用户手动释放。

不同点:

1、malloc和free是函数;new和delete是操作符。

2、malloc申请空间不会初始化;new会初始化。

3、malloc申请空间需要计算申请空间大小;new申请多个空间,只要在 \[\] 里输入你想开的对象个数。

4、malloc返回值是void*,C++中,必须强转;new不需要,他后面跟的就是类型。

5、malloc申请空间失败返回NULL,使用时必须手动判空;new不需要,不过要捕获异常。

6、申请自定义类型时,malloc/free不会调用构造函数和析构函数;new在申请空间后会调用构造函数对实例化出的对象进行初始化,delete会先调用析构函数,将申请的资源进行清理和释放,再释放空间。

相关推荐
guodingdingh3 分钟前
软件开发工作问题总结0718
java·开发语言·数据库
优橙教育2 小时前
5G网优培训 vs Java开发:转行选哪个?
java·开发语言·5g
同勉共进3 小时前
记一例 vibe coding + gcc bug 导致的线程池死锁问题
c++·线程池·gcc·死锁·vibe coding
我叫洋洋3 小时前
C ++ [ hello world ]
c语言·c++·算法
SeaTunnel4 小时前
从 Python Script 地狱到标准化数据集成框架
大数据·开发语言·python·程序员·代码·seatunnel
碎光拾影4 小时前
ARM交叉工具链各工具作用及IMX6ULL平台LED+蜂鸣器裸机程序实现
java·开发语言·数据库
圣光SG4 小时前
Servlet学习笔记
笔记·学习·servlet
奋发向前wcx4 小时前
y1,y2总复习笔记5 2026.7.19
数据结构·笔记·算法
Marst Code5 小时前
(python)2026Plotly 库评估:交互式可视化到底值不值得引入?
开发语言·python
Miao121315 小时前
微服务 API 测试实践:海外某民宿平台如何构建模式驱动测试基础设施
java·开发语言