在C

时间:2015-11-17 21:32:57

标签: c memory-management memory-leaks

我知道StackOverflow上有很多关于这个主题的答案,他们非常有帮助,但我不确定一件事。让我们说我有funcA和funcB:

char * funcA()
{
    char * arr = malloc(sizeof(char) * 20);

    //store data in arr...

    return arr;
}

void funcB()
{
    char * arr;
    while(up to some finite value)
    {
        arr = funcA();
        //do stuff with array

        /* Do I perform these two lines here every iteration?*/
        free(arr)
        arr = NULL;
    }

    /*Or do I perform it only once, at the end of the loop?*/
    free(arr)
    arr = NULL;
}

我认为arr应该在每次迭代中被释放。或者每次迭代都会覆盖" arr中的数据,因此只能在循环结束时调用free?这样做的正确方法是什么?感谢。

5 个答案:

答案 0 :(得分:7)

你需要在循环中调用free(arr),否则你会在循环的每次迭代中松开指向arr和泄漏内存的指针。

答案 1 :(得分:4)

您需要为每个malloc / calloc免费拨打电话。

char * funcA()
{
    char *arr = calloc(20, sizeof *arr); //allocation and initialize to 0
    if (arr) { //if successfully allocated
        //store data in arr...
    }
    return arr;
}

void funcB()
{
    char *arr;
    while (up to some finite value)
    {
        if ((arr = funcA())){ //if successfully allocated
            //do stuff with array

            free(arr);
            arr = NULL;
        } else {
            //allocation failed
            //deal with alloc error
        }
    }
}

您还应检查malloc错误,否则可能会出现分段错误

答案 2 :(得分:2)

  

/ *我每次迭代都会执行这两行吗?* /

是的,请确保在致电

后不将新内存地址分配给arr
arr = funcA();

并且在调用free之前,否则您将有内存泄漏,因为您将忘记funcA()返回的内存,并且将无法再释放它。

答案 3 :(得分:2)

每次执行malloc时,free也必须发生{/ p}}。

看看以下程序:

#include<stdlib.h>
#include<stdio.h>
#include<string.h>

char *funcA(void){
    char *arr = malloc(sizeof(char) * 20);

    strcpy(arr, "Michi");
    return arr;
}

void funcB(void){
    char *arr;
    int a = 0;

    while(a < 5){
        arr = funcA();
        printf("%s\n",arr);

        free(arr);
        arr = NULL;
        a++;
    }
}

int main(void){
    funcB();
    return 0;
}

这将输出Michi 5次:

Michi
Michi
Michi
Michi
Michi

正如您所看到的,有5 malloc和5 free,但如果我们free在阻止之外会发生什么?:

#include<stdlib.h>
#include<stdio.h>
#include<string.h>

char *funcA(void){
    char *arr = malloc(sizeof(char) * 20);

    strcpy(arr, "Michi");
    return arr;
}

void funcB(void){
    char *arr;
    int a = 0;

    while(a < 5){
        arr = funcA();
        printf("%s\n",arr);
        a++;
    }

    free(arr);
    arr = NULL;
}

int main(void){
    funcB();
    return 0;
}

您的程序可以正常运行且没有错误,但是有一个问题,您只需malloc次5次并且只使用free一次。

你有内存泄漏:

==3146== Command: ./program
==3146== 
Michi
Michi
Michi
Michi
Michi
==3146== 
==3146== HEAP SUMMARY:
==3146==     in use at exit: 80 bytes in 4 blocks
==3146==   total heap usage: 5 allocs, 1 frees, 100 bytes allocated
==3146== 
==3146== 80 bytes in 4 blocks are definitely lost in loss record 1 of 1
==3146==    at 0x4C2BBA0: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==3146==    by 0x400597: funcA (program.c:6)
==3146==    by 0x4005C7: funcB (program.c:17)
==3146==    by 0x400601: main (program.c:27)
==3146== 
==3146== LEAK SUMMARY:
==3146==    definitely lost: 80 bytes in 4 blocks
==3146==    indirectly lost: 0 bytes in 0 blocks
==3146==      possibly lost: 0 bytes in 0 blocks
==3146==    still reachable: 0 bytes in 0 blocks
==3146==         suppressed: 0 bytes in 0 blocks
==3146== 
==3146== For counts of detected and suppressed errors, rerun with: -v
==3146== ERROR SUMMARY: 1 errors from 1 contexts (suppressed: 0 from 0)

请记住,每次malloc free时。

答案 4 :(得分:1)

不,每次迭代都不会“覆盖”arr中的数据,每次迭代都需要释放内存