C++学习笔记(6):C++内存管理

注:转载请标明原文出处链接: https://lvxiaowen.blog.csdn.net/article/details/107009692

1 什么是内存管理?

在这里插入图片描述

2 内存分配方式

2.1 从静态存储区域分配

内存在程序编译的时候就已经分配好了,这块内存在程序的整个运行期间都存在。
例如全局变量,static静态成员变量

2.2 在栈(stack)上创建

执行函数时,函数内部变量的存储单元可以在栈上创建,函数执行结束时这些存储单元自动释放。栈内存分配运算置于处理器的指令集中,效率很高,但是分配的内存容量有限。

2.3 在堆(heap)上分配

也称为动态内存分配。程序在运行的时候用malloc或new申请任意多少内存,程序员自己负责在何时用free或delete来释放这块内存。动态内存的生命周期由程序员决定,使用非常灵活,但如果在堆上分配了空间,就有责任回收它,否则运行的程序会出现泄漏,频繁地分配和释放不同大小的堆空间将会产生堆内碎块。也就是我们常说的内存碎片。


3 堆和栈的区别

(1) 管理方式: 栈由编译器自动管理,无需手工控制;堆释放工作由程序员控制,容易产生memory leak。

(2) 空间大小: 一般来讲在32位系统下,堆内存可以达到4G的空间。但栈一般都是有一定的空间大小的。

(3) 碎片问题: 对于堆来讲,频繁的new/delete势必会造成内存空间的不连续,从而造成大量的碎片,使程序效率降低。栈则不会存在这个问题。

(4) 生长方向: 堆的生长方向是向上的,也就是向着内存地址增加的方向;栈的生长方向是向下的,是向着内存地址减小的方向增长。

(5) 分配方式: 堆都是动态分配的,没有静态分配的堆。栈有2种分配方式:静态分配和动态分配。静态分配是编译器完成的,比如局部变量的分配。动态分配由alloca函数进行分配,但是栈的动态分配和堆是不同的,它的动态分配是由编译器进行释放,无需手工实现。

(6) 分配效率: 栈是机器系统提供的数据结构,计算机会在底层对栈提供支持:分配专门的寄存器存放栈的地址,压栈出栈都有专门的指令执行,这就决定了栈的效率比较高。堆则是C/C++函数库提供的,它的机制是很复杂的,例如为了分配一块内存,库函数会按照一定的算法(具体的算法可以参考数据结构/操作系统)在堆内存中搜索可用的足够大小的空间,如果没有足够大小的空间(可能是由于内存碎片太多),就有可能调用系统功能去增加程序数据段的内存空间,这样就有机会分到足够大小的内存,然后进行返回。显然,堆的效率比栈要低得多。

4 内存的申请和释放

申请内存:int *p = new int;
释放内存:delete p;
申请块内存:int *arr=new int[10];
释放块内存:delete []arr;


内存申请是否一定成功?释放内存需要注意什么?
在这里插入图片描述
在这里插入图片描述

5 malloc/free与new/delete

在这里插入图片描述
(1) malloc/free是C程序中的库函数,需要头文件支持;new/delete是C++中的操作符,可以被重载。删除数组delete []p,指针释放后,要将指针置空。
(2) malloc和new都是在堆上分配内存。
(3) malloc分配内存失败时返回NULL;new内存分配失败时,会抛出bac_alloc异常。
(4) malloc/free是面向内存的,不可以调用构造函数和析构函数;new/delete是面向对象的,可以调用构造函数和析构函数,new可认为是malloc+构造函数。
(5) malloc不能初始化对象;new可以,如int *p = new int(2)。
(6) malloc返回的指针是void 类型,需要通过强制类型转换将void指针转换成我们需要的类型;而new返回的指针是它分配空间的类型。


参考资料

[1] https://www.imooc.com/learn/381
[2] C++内存管理
[3] 经典面试题之new和malloc的区别

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值