>我写了一个小的例子问题来了解内存分配和释放这个内存(以防止内存泄漏(:
#include <stdlib.h>
long* foo(char str[]) {
long *nums;
nums = calloc(2,sizeof(long));
//something is happening depending on what's inside the char[]
nums[0] = 57347534;
nums[1] = 84757;
return nums;
}
int main() {
char str1[400] = "This is a test";
long* retValue = foo(str1);
//some lines of checking content of "retValue"
char str2[400] = "This is another test";
retValue = foo(str2);
//some more lines of checking content of "retValue"
char str3[400] = "This is a final test";
retValue = foo(str3);
//again some more lines of checking content of "retValue"
free(retValue);
}
因此,在我的main
函数中,我使用了三个字符数组,我将传递给我的函数。此函数有一个长值的 num 指针,其中calloc
其中两个。然后我只是根据str[]
中的内容计算一些数字并返回nums
.
我对此的问题是:
- 如何释放用于
nums
的内存?因为我在使用它返回之前无法释放它。 - 释放最后一行的
retValue
是否正确? - 我不需要释放我的字符数组是对的,因为它们不是动态的?
感谢您的回答,这将有助于我更安全地使用指针!
您需要在每次新作业之前调用retValue
free
(如果以前的作业来自malloc
、calloc
或realloc
(。否则,您将有内存泄漏。
每个分配都必须匹配一个free
,简单明了。
回答有关内存分配和使用的问题的一个好方法是使用内存检查器 - 我将使用 Valgrind:
gcc-8 -std=c11 -fPIC -g -Wall -Wextra -Wwrite-strings -Wno-parentheses -Wpedantic -Warray-bounds 50627661.c -o 5062766
50627661.c: In function ‘foo’:
50627661.c:3:16: warning: unused parameter ‘str’ [-Wunused-parameter]
long* foo(char str[]) {
~~~~~^~~~~
valgrind -q --leak-check=full ./50627661
==14785== HEAP SUMMARY:
==14785== in use at exit: 32 bytes in 2 blocks
==14785== total heap usage: 3 allocs, 1 frees, 48 bytes allocated
==14785==
==14785== 16 bytes in 1 blocks are definitely lost in loss record 1 of 2
==14785== at 0x4C2EBA5: calloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==14785== by 0x10867F: foo (50627661.c:5)
==14785== by 0x1086F6: main (50627661.c:18)
==14785==
==14785== 16 bytes in 1 blocks are definitely lost in loss record 2 of 2
==14785== at 0x4C2EBA5: calloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==14785== by 0x10867F: foo (50627661.c:5)
==14785== by 0x108758: main (50627661.c:24)
这表明,在我们所做的三个分配中,我们只释放了其中一个 - 另外两个泄漏了。
如果您不想用free
来混淆您的调用代码,另一种方法是将调用者管理的数组传递给被调用者:
long foo(char str[], long *nums, int size) {
if (size < 2) { // passed array must be at least 2 long
return -1;
}
//something is happening depending on whats inside the char[]
nums[0] = 57347534;
nums[1] = 84757;
return 2; // returns used size (or -1 for error)
}
int main() {
long retValue[2];
char str1[400] = "This is a test";
if (-1 == foo(str1, retValue, 2)) {
// process error condition
}
//some lines of checking content of "retValue"
char str2[400] = "This is another test";
if (-1 == foo(str2, retValue, 2)) {
// process error condition
}
//some more lines of checking content of "retValue"
char str3[400] = "This is a final test";
if (-1 == foo(str3, retValue, 2)) {
// process error condition
}
//again some more lines of checking content of "retValue"
//free(retValue); no need for free since nothing was allocated...
return 0;
}