new 与 delete 的三种使用方法
new 表达式 与 new 操作符
1) new operator,也叫new表达式 ,就是我们惯常使用的new
string* ps = new string("abc");
上面这个new表达式完成了两件事情:申请内存和初始化对象。
2) operator new,也叫new操作符。
plan new , nothrow new , placement new (不知将placement new 归为此类是否正确)
1>> plan new
new操作符类似于C语言中的malloc,只是负责申请内存,例如:
void* buffer = operator new(sizeof(string));
注意这里多了一个operator。
在C++中是这样定义的:
void* operator new(std::size_t) throw(std::bad_alloc);
void operator delete(void *) throw();
提示:plain new在分配失败的情况下,抛出异常std::bad_alloc而不是返回NULL,
因此通过判断返回值是否为NULL是徒劳的。
2>> nothrow new 是不抛出异常的运算符new的形式。
nothrow new在失败时,返回NULL。定义如下:
void * operator new(std::size_t,const std::nothrow_t&) throw();
void operator delete(void*) throw();
例:
1. unsigned char *p = new(nothrow) unsigned char[length];
2. if(p == NULL) cout<<"allocate failed!"<<endl;
3. // ...
4. delete []p;
3>> placement new 它用于在给定的内存中初始化对象
这种new允许在一块已经分配成功的内存上重新构造对象或对象数组。
不用担心内存分配失败,因为它根本不分配内存,它做的唯一一件事情就是调用对象的构造函数。
定义如下:
void* operator new(size_t,void*);
void operator delete(void*,void*);
placement new是在指定位置初始化对象,也就是调用了构造函数,因此与之对应的就是析构函数了,
必须显示的调用类的析构函数释放对象。但此时内存空间仍然不会被释放,以供其他的对象使用。
组后仍然要调用 delete 释放内存空间
class A
{
public:
A();
~A();
private:
int a ;
int b;
};
void *pv = operator new(sizeof(A)) ;
pv = new(pv) (sizeof(A)) ;
static_cast(A*)(pv)->~A();
pv = NULL ;
主要应用场合:
1>> 的主要用途就是反复使用一块较大的动态分配的内存来构造不同类型的对象或者他们的数组。
2>> 构造起来的对象或其数组,要显示的调用他们的析构函数来销毁,千万不要使用delete。
与new对应的delete语法只有两种:
1. delete operator delete表达式
delete表达式和new表达式对应,完成对象的析构和内存的释放操作。
string* ps = new string("abc");
delete ps; //调用delete表达式,先析构再释放
2. operator delete delete操作符。
delete 操作符只是用于内存的释放,和C语言中的free相似。
例如:
void* buffer = operator new(sizeof(string));
operator delete(buffer); //释放
浙公网安备 33010602011771号