2014-05-04 183 views
-3

这两种释放二维数组的方法相似吗?删除二维数组C++

int** M = new int*[5]; 

for (int i = 0; i < 5; ++i) 
    M[i] = new int[3]; 

for (int i = 0; i < 5; ++i) { 
    for (int j = 0; j < 3; ++j) { 
     M[i][j] = i + j; 
    } 
} 

删除我:

for (int i = 0; i < 5; ++i) 
    delete [] M[i]; 
delete [] M; 

和删除II:

delete [] *M; 
delete [] M; 

是这两个代码相同呢?

+0

发生了什么事?你为什么不做广告? – Ben

+1

为什么不使用'的std :: vectors'?节省了很多麻烦 –

+0

的@EdHeal最好的办法是使用智能指针。但我感兴趣的指针和数组的工作现在 – Zeis45

回答

6

delete [] *M;delete [] M[0]相同,因此它不等同于删除循环中的所有M[i],因为只有第一个将被删除。循环是避免内存泄漏的正确方法。

或更好的是,使用std::vector而不是手动分配,你不需要担心删除指针。

5

它们不相似。他们不相似的明显原因是您要拨打new[] 6次,而在delete[]的第二个版本中,您要拨打“删除”2次。

delete [] *M; 
delete [] M; 

每次调用new[],你应该与delete[]匹配它,显然你不这样做。

如果您希望这两个调用delete[]匹配,您必须更改分配2d数组的方式。的变化会是这样:

int** M = new int*[5]; 
int *pool = new int[5*3]; 

for (int i = 0; i < 5; ++i, pool += 3) 
    M[i] = pool; 

在上面的例子中,只有2调用new[]制成,曾经为行指针,以及第二个用于存储池。然后循环只是在适当的地方将池中的每一行指针指向池中。

现在,“2调用”delete[]将正常工作,只要您在分配和释放数组之间不会做任何奇怪的事情,例如损坏的内存。

以这种方式分配2d数组的优点是new[]只被调用两次,而不管列的数量是多少。因此,如果您有10,000 x 10,000矩阵,您的原始版本需要拨打new[] 10,001次,而使用该池的版本只需要拨打new[]即可拨打2个电话。这很可能会加快程序的速度,因为分配器只被调用两次(然后再分配两次)。

另外,如果数组数据需要是连续的,那么上述方法是优选的,所以可以使用简单的指针运算来转到任何行或列。

但是,请确保:

  • 您的数组不改变尺寸和
  • 它不是衣衫褴褛(所有行必须具有相同的列数)。

否则,维护按我描述的方式分配的矩阵变得更加困难。