我知道如果我使用new[],我必须使用delete[],但这是我的疑问:
声明:
char **data; // This will be a bi-dimensional array构造:
data = new char*[10];
for (int i=0; i<10; ++i)
{
data[i] = new char[128];
}销毁:
for (int i=0; i<10; ++i)
{
delete data[i]; // <--- delete or delete[] ???
}
delete[] data;另一种情况是我有一个对象数组:
声明:
myClass **object;构造:
object = new myClass*[10];
for (int i=0; i<10; ++i)
{
object[i] = new myClass();
}销毁:
for (int i=0; i<10; ++i)
{
delete object[i]; // <--- this object[] is not an array, right?
}
delete[] object; // <--- Is this correct?发布于 2015-01-07 02:30:44
你基本上回答了你自己的问题。因为data[i]是一个数组,所以你需要delete[]。object[i]是用new分配的,所以你可以delete它。由于对象和数据都是数组,因此需要对它们执行delete[]操作。
发布于 2015-01-07 02:33:19
指针data的第一个维度是一个数组。第二个维度也是一个数组。因此,您必须使用delete[]来正确地释放从new[]中保留的内存。
对于您的对象,第一个维度是使用new分配的。所以你必须使用delete。然后在object上使用delete[],因为它是一个数组。
发布于 2015-01-08 00:03:55
您提到的助记符(delete []表示new [],delete表示new)是一个很好的实践,应该强制执行。
然而,当涉及到基类型(int、char、delete[] *等)和类时,delete和void之间存在巨大的差异。
new和malloc的不同之处在于,一个调用构造函数,而另一个不调用。对于析构函数,delete和free也有同样的关系。
在您的示例中,您给出了两种情况:一种是分配了简单类型的数组,另一种是分配了对象数组。
行为是不同的。
对于简单类型,delete和delete[]将产生相同的结果。
原因?好的,您基本上分配了一个由10个char*指针组成的块,所以删除它是没有问题的(分配的内存分页将被释放)。
换句话说,如果你有
char* a = new char[100];然后
delete a;和
delete[] a;将产生相同的结果(请注意,您使用了新的[]);
当涉及到具有构造函数和析构函数的对象时,这种行为是不同的。
让我们以下面的类为例:
class SimpleClass
{
public:
SimpleClass(){printf("constructed");
~SimpleClass()(printf("destructed");
}和以下代码:
SimpleClass* arr1 = new SimpleClass[5];
SimpleClass* arr2 = new SimpleClass[5];
char* arr3 = new char[5];
char* arr4 = new char[5];
delete[] arr4;
delete arr3;
delete[] arr2;
delete arr1; //notice the surprise ?在Visual Studio中运行上面的代码(如果可以)并打开一个内存查看器。您将看到,在ptrs arr4和arr3上分配的内存已正确失效,arr2也是如此。
但是,当尝试在不使用[]调用的情况下删除arr1时,您将得到一个SigSev错误。
为什么?
因为在arr2的情况下,您有一个已分配对象的数组,而delete[]语句意味着“传递数组中的每个析构函数”。
在arr1的情况下,它意味着:调用在指针arr1处分配的对象的析构函数...如果考虑到在该地址上分配了超过1个对象,并且最终尝试释放小于初始分配大小的页,则有点不幸。
底线:
new[]的delete[]和新的delete!
每次都有效!
https://stackoverflow.com/questions/27804671
复制相似问题