有时候,我们会在某些地方看到new operator/delete operator与operator new/operator delete这两组相似的组合,对于见过后者的人,可能会觉得这两者本就是同样的东西,只是前者写错了而已。其实不然,两者确实是截然不同的东西。

    new operator/delete operator,其实就是我们常用来动态分配空间的new和delete操作符,operator也有运算符的意思,注意new和delete是运算符!而operator new/operator delete,它们不是运算符,而是两个函数,同样用以分配空间。此时,或许有人会有疑问了,既然是相同的功能,定义两组,是不是做无用功了?答案是否定的,这不是做无用功!下面我们来看一段代码及两次运行结果,来分析分析两者异同:

 1 class Test
 2 {
 3 private:
 4 
 5 public:
 6     Test() { cout << "Constructor of Test!" << endl; }
 7     ~Test() { cout << "Destructor of Test!" << endl; }
 8 };
 9 
10 int main(int argc, char argv[])
11 {
12     //Test *test = (Test*)operator new(sizeof(Test));
13     //cout << test << endl;
14     //operator delete(test);
15     Test *test = new Test();
16     cout << test << endl;
17     delete test;
18 
19     return 0;
20 }

    未注释段是运用new,delete运算符分配空间,注释段则是调用operator new/operator delete函数进行分配空间。我们可以很明显地从代码及运行结果中发现几个问题:

    1.为何调用operator new/operator delete时,Test类的构造函数、析构函数均未被调用,而使用new/delete运算符则调用了?

    2.为何调用operator new/operator delete得到空间地址后要进行强制转换,而使用new/delete运算符则不需要?

    这就是new/delete运算符与operator new/operator delete函数的区别了。虽然同样是用来分配空间的,但new/delete运算符会对相应的类构造函数、析构函数进行调用,而operator new/operator delete函数则不会,它只单纯的分配一块空间;再有,new运算符返回的是一个该类对象的指针,而operator new函数则返回一个void*类型,因此需要一步强制转换的过程。

    提到两者区别,有几点需要提出:

    1.new operator/delete operator不可且不应该被重载,这是C++标准要求的;

    2.operator new可以被重载,但返回值类型必须为void*(operator delete同样可被重载);

    3.operator new重载时,第一个参数必须为表达分配空间的大小(单位为字节),为size_t类型;

    4.operator new重载时,满足第三个条件,则可以带其他参数。

    PS:最后再提一点,动态分配的空间必须手动释放,C++不具备垃圾回收机制,所以不能放任动态分配的空间不管。用了new就必须用delete,用了operator new就必须用operator delete(new[], operator new[]同理)。operator new分配的空间不能用C库中的free释放,两者具有不同的内存使用登记方式。