我创建了一个旨在获取用户输入的函数。它要求将内存分配给保存用户输入的变量;但是,该函数在函数结束时返回。释放已分配内存/返回变量值的正确方法是什么?
以下是代码:
char *input = malloc(MAX_SIZE*sizeof(char*));
int i = 0;
char c;
while((c = getchar()) != '\n' && c != EOF) {
input[i++] = c;
}
return input;
我应该返回输入地址并在使用后将其释放吗?
对于释放输入变量的最合适方法感到好奇。
答案 0 :(得分:15)
这很简单,只要你传递free()
malloc()
所返回的同一指针就可以了。
例如
char *readInput(size_t size)
{
char *input;
int chr;
input = malloc(size + 1);
if (input == NULL)
return NULL;
while ((i < size) && ((chr = getchar()) != '\n') && (chr != EOF))
input[i++] = chr;
input[size] = '\0'; /* nul terminate the array, so it can be a string */
return input;
}
int main(void)
{
char *input;
input = readInput(100);
if (input == NULL)
return -1;
printf("input: %s\n", input);
/* now you can free it */
free(input);
return 0;
}
你永远不应该做的事情就像
free(input + n);
因为input + n
不是malloc()
返回的指针。
但是您的代码还有其他问题需要处理
您正在为MAX_SIZE
char
分配空间,因此您应该乘以sizeof(char)
1
,而不是sizeof(char *)
,这将分配MAX_SIZE
MAX_SIZE
指针,也可以使main()
成为函数参数,因为如果要分配固定缓冲区,可以在MAX_SIZE
中定义一个大小为char input[MAX_SIZE]
的数组readInput()
,并将其作为参数传递给malloc()
,从而避免free()
和while
。
您正在分配那么多空间,但是在i < MAX_SIZE
循环中没有防止溢出,您应该验证{{1}}。
答案 1 :(得分:4)
您可以编写一个返回类型为char*
的函数,返回input
,并要求用户在完成数据后调用free
。
您还可以要求用户自己传入适当大小的缓冲区以及缓冲区大小限制,并返回写入缓冲区的字符数。
答案 2 :(得分:1)
这是一个经典的案例。函数mallocs为其结果的内存,调用者必须释放返回的值。你现在正走在内存泄漏的薄冰上。 2个原因
第一;您无法以可执行的方式传达免费需求(即编译器或运行时无法帮助您 - 与指定参数类型的对比)。你只需要在某处记录它,并希望调用者已经阅读了你的文档
第二:即使调用者知道释放结果他可能会犯错误,也会采取一些不会释放内存的错误路径。这不会导致立即错误,事情似乎有效,但在运行3周后,您的应用程序在内存不足后崩溃
这就是为什么这么多现代的&#39;语言专注于这个主题,c ++智能指针,Java,C#等垃圾收集,......