2020-12-11

Malloc和New的区别

说到malloc就不得不要了解堆和栈两片内存区。

首先说一下堆区。它是一块公有的内存区,被分为全局堆和局部堆。全局堆是还未被使用的内存,局部堆是用户分配的空间。堆在操作系统初始化进程的时候分配,用户也可以在运行的时候额外申请空间,使用结束后必须要释放掉还给操作系统,否则会造成内存泄露。

栈是线程独有的,用于保存线程的运行状态和局部变量参数。每一条线程都有独立对应的栈,每一个函数也有独立的栈。栈被用来在函数间传递参数。简单的说栈是编译器分配的,存放函数的参数和局部变量。

再来说一下malloc,它是c/c++的标准函数,malloc函数时必须要指定大小,函数返回的是一个void*指针,需要强转类型。在使用完这块空间时必须要用free手动释放空间,不然会造成内存泄露。同时不能交叉释放或者重复释放,不然会发生未知错误。

简单说一下为什么不释放会造成内存泄露以及交叉释放或者重复释放带来的后果。首先用户分配的空间都是在堆上开辟的,在堆上malloc实际上管着一串很长的空闲列表,这块列表是有很多空闲内存块组成的,就类似链表一样。当用户请求空间时,就会在这块空闲列表上搜索符合用户大小的空间,找到这块内存后会从空闲列表中脱离供用户使用,当使用结束释放这块内存后,它又会被重新加到空闲列表中去。想象一下,如果每一块内存都不释放,那么空闲列表最后会没有可用内存,没办法只能覆盖一块内存了,这样的后果可想而知。
再看一下重复释放问题。free函数是通过指针去寻找这块内存的,因为它只是一个指针,所以指针是保存在栈上的,而开辟的空间是在堆上的,第一次释放掉堆上的空间后,这块空间就被回收,此时很有可能这块空间又被其他程序使用,第二次释放就把其他程序使用的空间给释放掉了,肯定会造成严重的后果。

挺重要的一点就是在哪里开辟就在哪里释放掉最安全。举个例子在一个局部函数中用malloc申请了一块内存,之后在主函数中给它释放掉。要知道随着局部函数的结束,函数所在的栈被销毁,指针也被销毁了,而指针所指的那块空间是在堆上的,所以还是没被释放。

New是在malloc改进而来,内部实现还是通过malloc,但是比malloc更加智能,它是返回指定数据类型的指针,同时会自动计算出所需空间大小。比如
int *p = new int 它会自动开辟一块sizeof(int)大小的空间。为啥说智能呢?在对象创建前它会自动执行默认构造函数来初始化,而在对象消亡前会自动执行析构函数,这点是c没有的

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值