C++ C++;指针内存泄漏数组

C++ C++;指针内存泄漏数组,c++,memory-leaks,valgrind,C++,Memory Leaks,Valgrind,在我的类中,我有一个动态分配的指针数组。我的声明: array = new Elem* [size]; for (int i = 0; i < size; i++) { array[i] = NULL; } 我认为这是正确的,valgrind报告0个未释放的块,这是完美的,但它报告 Mismatched free() / delete / delete [] 正好在“delete array;”所在的行上是我也尝试过“删除[]数组”,但那也只是“1个未释放的块”而已!如果

在我的类中,我有一个动态分配的指针数组。我的声明:

 array = new Elem* [size];
 for (int i = 0; i < size; i++) {
    array[i] = NULL;
 }
我认为这是正确的,valgrind报告0个未释放的块,这是完美的,但它报告

Mismatched free() / delete / delete []
正好在“delete array;”所在的行上是我也尝试过“删除[]数组”,但那也只是“1个未释放的块”而已!如果有人能给我解释一下,我将不胜感激

编辑: 因此,使用:

for (int i = 0; i < size; i++) {
   delete array[i];
}
delete[] array;
站着

EDIT2: 我也解决了这个问题,谢谢你的贡献

您需要:

delete [] array;
因为它是一个数组

我只是注意到你的便条上说你也尝试过这个-这是正确的做法,所以我不知道为什么你仍然会出错

编辑:这应该得到更彻底的解释

使用
new
创建指针时,指针可能指向单个元素或元素数组,具体取决于使用的语法。但指针类型在这两种情况下是相同的!编译器依赖于您知道指针指向什么,并相应地处理它

Elem ** single = new Elem*;    // pointer to one pointer
single[0] = new Elem;          // OK
single[1] = new Elem;          // runtime error, but not compile time

Elem ** array = new Elem* [2]; // pointer to array of pointers
array[0] = new Elem;           // OK
array[1] = new Elem;           // OK
删除指针时,将为指针指向的对象或数组的每个元素调用析构函数。但是,由于指针类型在每种情况下都是相同的,编译器依赖于您为它提供正确的语法,以便它知道该做什么

delete single;
delete [] array;

在您的例子中,数组的元素也是指针,指针没有析构函数。这意味着这些指针不会被删除,如果您不先删除它们,它们将成为内存泄漏。在最终删除之前,您可以使用一个循环来分别删除它们。

删除数组的语法如下所示:

delete[] array;
您的
for
循环可以删除数组元素指向的对象。删除数组本身是唯一的问题。您需要同时执行
for
循环,然后执行
delete[]
来处理数组本身

for (int i = 0; i < size; i++) {
   delete array[i];
}
delete[] array;
for (int i = 0; i < size; i++) { // only free inside if dynamically allocated - not if just storing pointers
   delete array[i];
}
delete[] array; // necesarry
for(int i=0;i
我怀疑您尝试过使用
for
循环或
delete[]
,但不是同时使用两者。如果这样做时仍然存在泄漏或错误,那么需要向我们展示分配作为数组元素的指针的代码



使用
std::vector
而不是数组将意味着您可以不再担心这些细节,而转向更高的抽象级别。

您应该释放数组中的所有内容(如果动态分配),然后释放数组本身

for (int i = 0; i < size; i++) {
   delete array[i];
}
delete[] array;
for (int i = 0; i < size; i++) { // only free inside if dynamically allocated - not if just storing pointers
   delete array[i];
}
delete[] array; // necesarry
for(int i=0;i
在这种情况下,两者都需要

for(int i=0;i
每次调用
new
时,您只需调用一次
delete


请注意,尽管您需要在此处调用
delete[]array
(因为您为它分配了
new[]
),但
delete[]
操作符不会调用数组元素指向的对象上的析构函数。这是因为
delete[]
操作符对数组中的对象调用析构函数,并且数组包含指针,但不包含对象。指针本身没有析构函数。

哪里说分配了未释放的块?让您的生活更轻松:删除所有上述内容,然后使用Boost。我知道这并不能回答您的问题,但有什么原因不能使用std::vector来大大简化内存管理吗?确实有,这是一个学校作业,我们不允许使用它,可能关键是要学习如何正确地完成它。@aGr:“家庭作业”标签在这种情况下合适吗?这可能也会阻止其他人推动矢量角度。:)OP确实需要
delete[]
,但我不会称它为数组。@cnicutar,如果它不是数组,你会怎么称呼它?
new[]
语法分配一个数组。@cnicutar,是的,一个指向数组的指针。我希望我们现在能达成一致。这是一个数组(好吧,一个指向数组的指针)。尽管它与@cnicutar的“array type”不同,但我必须根据您的评论进行更正-指针类型实际上是指向单个元素的指针,但它指向的内存仍然是数组。不知何故,内存子系统会跟踪差异。你的意思是他应该删除数组中指针指向的所有对象,然后使用
delete[]
删除数组中的对象(指针)和数组本身。@DavidSchwartz,说数组中的对象被删除是不准确的,相反,它们被摧毁了。指针没有析构函数,因此在该步骤中不会发生任何事情。@markransem指针有析构函数。C++使它们具有与内置类型相关的模板。<代码> DEL> []/CODE>的语义是删除数组中的对象。在本例中,这没有多大作用,但关键是说
delete[]
不能“释放数组中的所有内容”是错误的。OP的问题是他有一个指针数组。@DavidSchwartz:Mark是正确的。每个元素都会被销毁(由于使用了微不足道的析构函数,所以对原始指针来说是不可操作的),然后立即释放整个块。每个元素都不是单独释放的。我认为在形式上,指针类型有一些无关紧要的析构函数,它们什么也不做。@David好的,我编辑过它。令人惊讶的是,在所有的噪音中,信号是如何得到很多的。
for (int i = 0; i < size; i++) { // only free inside if dynamically allocated - not if just storing pointers
   delete array[i];
}
delete[] array; // necesarry
for (int i = 0; i < size; i++) {
   delete array[i];
}
delete[] array;