程序内存区域
在介绍内存分配之前,首先介绍下c/c++程序的内存区域分布。其主要分为:代码区、静态存储区、栈区、堆区、常量区。
代码区:程序代码和立即数存储区域
静态存储区:全局变量和静态变量存储区域
栈区:有程序自动分配和释放的区域,如:局部变量
堆区:用户new或者malloc分配的内存区域,统一由用户使用和管理,使用完后需要用delet或者free释放,否则造成内存泄露
常量区:字符常量存储区域
内存的分配和释放
用户自定义内存的声请由new或者malloc进行,释放由对应的delete和free进行。
new与malloc
new分配内存时自动计算分配的内存大小,不需要额外的计算,直接返回需要的指针类型。
malloc分配内存时需要给定分配的内存大小,同时返回的是void*指针,需要强制转换为需要的类型。
new分配内存时能够进行初始化,malloc不能。
new在分配用户自定义数据类型,将自动调用其构造函数。
delete和free
delete用于释放new分配的内存;free用于释放malloc分配的内存。
delete在释放用户自定义数据类型时,将自动调用其析构函数。
new和new[]、delete和delete[]
new[]和delete[]用于分配和释放数组指针;new和delete用于分配和释放变量。
在new[]分配的指针类型为简单数据类型时(标准库支持的数据类型,如int、char、short等),可以用delete释放new[]分配的内存;但是当new[]分配的数据类型为用户自定义类型时(如:对象),就只能用
delete[]释放new[]分配的内存,只是因为delete[]将会一一调用用户自定义数据类型的析构函数,完成内存释放。
最好,将new与delete、new[]和delete[]配对使用。
new和malloc的线程安全性
new和malloc都不是线程安全的,只是因为它们使用了一个类似全局线性链表的结构用于存储内存分配。
注意:
在对指针进行new或者malloc后,如果修改了指针指向的值(如:指针加一)后,则会在debug版本中造成释放内存错误,虽然在release版本中正常,当时仍然造成内存泄露。解决方法可以在修改指针的值前,用一个临时指针存储该指针的值,在需要释放处,直接释放临时指针就好了,如果记得将临时指针和源指针值为NULL,避免野指针。