今天学习动态内存管理malloc函数时,发现了一个小问题,再经过查阅资料,和实验验证后,终于明白了问题所在。
首先,我们先来看问题:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
int main()
{
int* parr = (int*)malloc(100, sizeof(int));
*(parr++) = 0;
printf("%d\n", parr[1]);
free(parr);
parr = NULL;
return 0;
}
运行失败;
遇到这个问题的时候也是一脸懵,为甚么会报错呢?
于是我尝试吧free删掉,结果程序就正常了。
这时候,程序又正常了。
那么,我们现在换个思路:
int main()
{
int* parr = (int*)malloc(100, sizeof(int));
/**(parr++) = 0;*/
printf("%d\n", parr[1]);
free(parr);
parr = NULL;
return 0;
}
把第二行的代码注释了发现,程序又能正常运行了。
查阅了相关资料才知道:
当malloc()之后,test就指向了malloc()函数分配的一个内存块。
而parr++时,parr指向的地址不再是malloc创建内存块的首地址,而是parr[1]这个常量地址。
因此free(parr)释放一个常量地址是极其不合理的。
我们的猜想对不对呢? 下面到了测试猜想的环节
思路:再加一个指针 int* p=parr 指向malloc创建的首地址,如果free(p)成功,证明思路正确。
运行成功!
总结解决方法:
增加一个指针变量 buf_src,用于保存原指针 buf 的地址,
现在 free(buf_src),既是对 malloc 时 指针 buf 地址空间的释放。
将原指针const常量化,保护指针
指向malloc申请的内存的指针,在运用过程中指针的指向千万不要改变,
就算要改变也要用另外一个变量保存malloc申请的内存的地址,最后用free释放,否则会导致内存泄露。