C:正确释放的多维阵列的存储器 [英] C: Correctly freeing memory of a multi-dimensional array

查看:124
本文介绍了C:正确释放的多维阵列的存储器的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设你有下面的ANSI C code,它初始化一个多维数组:

  INT的main()
{
      INT I,M = 5,N = 20;
      INT ** A =的malloc(M *的sizeof(INT *));      //初始化数组
      对于(i = 0; I<米;我++){
          一个由[i] =的malloc(N * sizeof的(INT));
      }      //...do使用数组的东西      //我如何释放一个**?      返回0;
}

使用在 ** A ,我该如何正确地从内存中释放呢?


[更新] (解决方案)

感谢蒂姆(和其他人)<一个href=\"http://stackoverflow.com/questions/1733881/c-correctly-freeing-memory-of-a-multi-dimensional-array/1733945#1733945\">answer,我现在可以做这样的功能,以腾出从我的多维数组的内存:

 无效freeArray(INT **一,诠释米){
    INT I;
    对于(i = 0; I&LT;米; ++ I){
        免费(A []​​);
    }
    自由(一);
}


解决方案

确定,有困惑的解释公平的交易究竟什么样的顺序
必要免费()调用必须在,所以我会尽力澄清
人们想要知道的,为什么。

从基础开始,以释放已分配的内存
使用的malloc(),您只需拨打免费()与完全指针
你被给出的malloc()。因此,对于这个code:

  INT ** A =的malloc(M *的sizeof(INT *));

您需要一个匹配的:

 免费(一);

和该行:

  A [I] =的malloc(N * sizeof的(INT));

您需要一个匹配的:

 免费(A []​​);

相似的循环中。

如果这变得复杂在此需要发生的顺序。如果
你叫的malloc()几次去几个不同的块
记忆中,一般不要紧,你叫什么顺序免费()
你与他们完成。但是,为了在这里重要的一个非常
具体原因:您正在使用的malloc ED内存一大块举行
该指针的malloc ED存储器的其他块。因为你的必须
的尝试读取或写入内存,一旦你已经把它递了回来
免费(),这意味着你将不得不释放块用
存储在的一个指针[I] 的你释放 A 块本身。
使用指针个别块存储在 A [I] 不依赖于各
另外,等都可以免费 D在你最喜欢的顺序。

所以,把这个都在一起,我们得到这样的:

 为(i = 0; I&LT;米;我++){
  免费(A []​​);
}
自由(一);

最后一个提示:当调用的malloc(),可考虑改变这些:

  INT ** A =的malloc(M *的sizeof(INT *));一个由[i] =的malloc(N * sizeof的(INT));

  INT ** A =的malloc(M *的sizeof(* a)条);一个由[i] = malloc的(N * sizeof的(*(一个由[i])));

这是什么做的?编译器知道 A INT ** ,所以可以
确定的sizeof(* A)相同的sizeof(INT *)。然而,如果
以后你改变主意,想字符 s或 s或 s或
无论你的阵列,而不是 INT S IN,或者你适应这个code供以后
在别的用,你就必须改变只是一个剩余
参照 INT 在上面的第一个报价行,以及其他一切
会自动落入你的地方。这消除了可能性
的错误被忽视的未来。

祝你好运!

Say you have the following ANSI C code that initializes a multi-dimensional array :

int main()
{
      int i, m = 5, n = 20;
      int **a = malloc(m * sizeof(int *));

      //Initialize the arrays
      for (i = 0; i < m; i++) { 
          a[i]=malloc(n * sizeof(int));
      }

      //...do something with arrays

      //How do I free the **a ?

      return 0;
}

After using the **a, how do I correctly free it from memory ?


[Update] (Solution)

Thanks to Tim's (and the others) answer, I can now do such a function to free up memory from my multi-dimensional array :

void freeArray(int **a, int m) {
    int i;
    for (i = 0; i < m; ++i) {
        free(a[i]);
    }
    free(a);
}

解决方案

OK, there's a fair deal of confusion explaining exactly what order the necessary free() calls have to be in, so I'll try to clarify what people are trying to get at and why.

Starting with the basics, to free up memory which has been allocated using malloc(), you simply call free() with exactly the pointer which you were given by malloc(). So for this code:

int **a = malloc(m * sizeof(int *));

you need a matching:

free(a);

and for this line:

a[i]=malloc(n * sizeof(int));

you need a matching:

free(a[i]);

inside a similar loop.

Where this gets complicated is the order in which this needs to happen. If you call malloc() several times to get several different chunks of memory, in general it doesn't matter what order you call free() when you have done with them. However, the order is important here for a very specific reason: you are using one chunk of malloced memory to hold the pointers to other chunks of malloced memory. Because you must not attempt to read or write memory once you have handed it back with free(), this means that you are going to have to free the chunks with their pointers stored in a[i] before you free the a chunk itself. The individual chunks with pointers stored in a[i] are not dependent on each other, and so can be freed in whichever order you like.

So, putting this all together, we get this:

for (i = 0; i < m; i++) { 
  free(a[i]);
}
free(a);

One last tip: when calling malloc(), consider changing these:

int **a = malloc(m * sizeof(int *));

a[i]=malloc(n * sizeof(int));

to:

int **a = malloc(m * sizeof(*a));

a[i]=malloc(n * sizeof(*(a[i])));

What's this doing? The compiler knows that a is an int **, so it can determine that sizeof(*a) is the same as sizeof(int *). However, if later on you change your mind and want chars or shorts or longs or whatever in your array instead of ints, or you adapt this code for later use in something else, you will have to change just the one remaining reference to int in the first quoted line above, and everything else will automatically fall into place for you. This removes the likelihood of unnoticed errors in the future.

Good luck!

这篇关于C:正确释放的多维阵列的存储器的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆