C++——内存管理
Primitives基础

C++内存分配的四个Prinitives:

区别:

- 第7行
::operator new(512)实际上类似第1行的malloc(512),调用的就是malloc,第8行也类似第2行; malloc/free只是申请了一段连续的空间,而new/delete则是针对对象,释放时会调用析构函数;#ifdef后面定义了在不同平台使用的接口,前两个类似是对象调用,用.运算符,第三个是静态,可以直接用类名+::运算符调用。

C++ new/delete
C++ new做两件事:分配内存、调用构造函数(相当于封装了malloc)
Complex *pc = new Complex(1, 2)
执行如下:
Complex *pc;
try{
// operator new运算符是可以重载的,::operator new则是一个全局的函数
1. void *mem = operator new(sizeof(Complex)); // allocate (相当于malloc的工作)
2. pc = static_cast<Complex*>(mem); // cast
3. pc -> Complex::Complex(1, 2); // construct
}
catch(std::bad_alloc){
// 若allocation失败就不执行constructor
}
C++delete做两件事加粗样式**:先析构、在释放内存(相当于封装了free)
...
delete pc;
执行如下:
1. pc -> ~Complex(); // 先析构
2. operator delete(pc); // 再释放内存
C++ new[]/delete[]
C++ array new:容易发生内存泄漏
会有cookie记录新申请的内存空间相关的信息(如地址、长度等)
Complex *pac = new Compex[3];
// 调用三次构造函数
// 无法通过参数赋初值
...
delete[] pca; // 调用三次析构函数
内存泄漏是发生在delete调用析构函数的时候,主要是存在指针的情况下:

如果不加[],三个内存只释放了一块,另两个仍然存在指针。
malloc会申请一下的内存:
int *pi = new int[10]; // sizeof(pi) : 4
delete pi; // []对于整数无所谓,因为不需要调用析构函数

C++ new()
C++ placement new:允许我们将对象建构于已经分配的内存中(allocated memory),没有对应的placement delete,因为它根本没有分配内存。
char *buf = new char[sizeof(Complex) * 3];
Complex *pc = new(buf)Complex(1, 2);
...
delete[] buf;
执行如下:
Complex *pc;
try{
1. void *mem = operator new(sizeof(Complex), buf); // 定点,不分配内存
2. pc = static_cast<Complex*>(mem);
3. pc -> Complex::Complex(1, 2);
}
catch(std::bad_alloc){
// 若allocation失败则不执行构造
}

1188

被折叠的 条评论
为什么被折叠?



