delete与delete[]的区别和使用方法

来源:互联网 发布:杭州网络推广公司 编辑:程序博客网 时间:2024/05/16 03:43

由new分配的一个数组空间,比如说 int *array=new int[50],当用delete释放这个空间时,用语句delete []array和delete array是否等价! 

C++告诉我们在回收用 new 分配的单个对象的内存空间的时候用 delete,回收用 new[] 分配的一组对象的内存空间的时候用 delete[]。 

关于 new[] 和 delete[],其中又分为两种情况:(1) 为基本数据类型分配和回收空间;(2) 为自定义类型分配和回收空间。 

对于 (1),上面提供的程序a可以证明了 delete[] 和 delete 是等同的。 
程序a: 
#include <stdio.h> 
#define BUFF_SIZE 10240 
int main(int argc, char *argv[]) 

printf("Hello, world\n"; 
char* p = NULL; 
while(1) 

p = new TTT[BUFF_SIZE]; 
printf("0x%08XH\n",p); 
Sleep(5000); 
delete p; //或者delete [] p; 
p = NULL; 

return 0; 


但是对于 (2),情况就发生了变化。请看下面的程序。 
#include <stdio.h> 
#define BUFF_SIZE 10240 

class TTT 

public: 
TTT() 

//aa = new char[1024]; 
}; 
~TTT() 

//delete [] aa; 
//printf("TTT destructor()\n"; 
}; 
private: 
int a; 
char* aa; 
int inta[1024]; 
}; 

int main(int argc, char *argv[]) 

printf("Hello, world\n"; 
TTT* p = NULL; 
while(1) 

p = new TTT[BUFF_SIZE]; 
printf("0x%08XH\n",p); 
delete p; //delete [] p; 
p = NULL; 

return 0; 


大家可以自己运行这个程序,看一看 delete p1 和 delete[] p1 的不同结果,我就不在这里贴运行结果了。 

从运行结果中我们可以看出,delete p 在回收空间的过程中,只有 p[0] 这个对象调用了析构函数,其它对象如 p[1]、p[2] 等都没有调用自身的析构函数,在析构函数中的内存释放操作将不会被执行(引发内存泄漏),已使用内存不断增加,这就是问题的症结所在。如果用 delete[],则在回收空间之前所有对象都会首先调用自己的析构函数,已使用内存不会不断增加。 

基本类型的对象没有析构函数,所以回收基本类型组成的数组空间用 delete 和 delete[] 都是应该可以的;但是对于类对象数组,只能用 delete[]。对于 new 的单个对象,只能用 delete 不能用 delete[] 回收空间。
参考资料:http://dev.csdn.net/develop/article/38/38316.shtm

作者后续相关文章:

昨天写了一篇关于delete和delete[]的文章,有位仁兄指出我的结论是错误的,那样的结果只会在特定的编译器程序。为了不会误导大家,文章意见删除。回家后仔细看了《Effective C++》,是我看书太不仔细了,虽然忘了那位仁兄是谁了,在这里还是谢谢你。现将《Effective C++》中正确的观点、结论摘录如下:

1.              当你使用new时,有两件事会发生。第一,内存被配置(透过函数operator new)。第二,会有一个(或以上)的constructors针对此内存被调用。当你使用delete时,也有两件事发生:一个(或以上)的destructors会针对此内存被调用,然后内存被释放(透过函数operator delete)。

2.              如果你使用delete是未加括号,delete便假设删除对象是单一对象。否则便假设删除对象是个数组。

3.              string *stringPtr1 = new string;

string *stringPtr2 = new string[100];

……

delete stringPtr1;

delete [] stringPtr2;

如果你对着stringPtr1使用“[]”形式,其结果未定义。如果你对着stringPtr2没有使用“[]”形式,其结果亦未定义。犹有进者,这对内建型别如int者亦未定义,即使这类型别并没有destructors。

4.              因此,游戏规则很简单,如果你在调用new时使用了[],则你在调用delete时也使用[],如果你在调用new的时候没有[],那么你也不应该在调用时使用[]。


转自:http://hi.baidu.com/shijg/blog/item/f1b24d16d4b4774920a4e987.html

原创粉丝点击