【发布时间】:2014-09-20 13:29:18
【问题描述】:
我正在学习 Learn C the Hard way 在线课程。在下面的代码示例中,我不明白为什么需要两个 free() 调用。我以为只需要调用一次free(),因为只有一个malloc() 出现。有人能解释一下为什么我们需要两个吗?
如果我将 free(who->name); 注释掉,那么 valgrind 会告诉我我丢失了一大块记忆,就像这样;
LEAK SUMMARY:
definitely lost: 21 bytes in 2 blocks
代码如下:
#include <stdio.h>
#include <assert.h>
#include <stdlib.h>
#include <string.h>
struct Person {
char *name;
int age;
int height;
int weight;
};
struct Person *Person_create(char *name, int age, int height, int weight)
{
struct Person *who = malloc(sizeof(struct Person));
assert(who != NULL);
who->name = strdup(name);
who->age = age;
who->height = height;
who->weight = weight;
return who;
}
void Person_destroy(struct Person *who)
{
assert(who != NULL);
free(who->name); /* Why this one??! */
free(who);
}
int main(int argc, char *argv[])
{
// make two people structures
struct Person *joe = Person_create(
"Joe Alex", 32, 64, 140);
struct Person *frank = Person_create(
"Frank Blank", 20, 72, 180);
// destroy them both so we clean up
Person_destroy(joe);
Person_destroy(frank);
return 0;
}
【问题讨论】:
-
因为 strdup() 也分配了内存,所以它必须被释放(参见doc)。
-
strdup是伪装的malloc。 -
阅读标准函数的文档比在 SO 上提问要更快!
-
strdup不是标准 C 函数,但它在 POSIX 中。 (除了malloc、calloc、realloc之外,没有标准 C 函数返回需要释放的指针。 -
在 C99 以外的其他标准中可以提及标准函数。 Posix 就是这样一个标准。