C语言里如何使用free()释放字符串内存

在C++里有delete和delete[]以区别单个变量与数组,但是C语言里只有free(),请问它是如何区别一个指针所指向的是单个变量还是一个数组呢?
char *p1, *p2, *p;
p1=malloc(20);
p2=malloc(40);
memset(p1, 'a', 20);
memset(p2, 'b', 40);

p1[5]='/0';
p=p1;
free(p); /* 它怎么知道要释放多少内存?能正确释放吗? */

p2[10]=0;
p=p2;
free(p); /* 它怎么知道要释放多少内存?能正确释放吗? */

由于free和malloc配对使用,malloc的时候,大小已经告诉系统了。

free的时候,系统会比对一下这个地址,是不是malloc申请的,如果不是,不给释放

如果是的话,系统就知道要释放多大内存,因为malloc的时候,系统有记录的。

当然了,申请的地址,也记录了的,否则,就无法比对了。

#include <stdio.h>
#include <stdlib.h>
int main()
{
int *p;

p=(int *)malloc(sizeof(int)*3);
p[0]=1;p[1]=2;p[2]=3;
p++;
//free(p);/////////由于p++过,已经不是malloc申请的那个地址了,因此这句运行会报错
p[0]=4;
free(p-1);//这句倒是正确的,因为经过p++,这里的p-1刚好是malloc申请的地址
return 0;
}

另外,问你一个同样的问题:
char *p1 = new char[10];
char *p2 = new char[20];
delete p1[];
delete p2[];
释放p1和p2的时候,没有指明大小,它怎么知道p1是10,p2是20的呢?
如果不知道,它怎么去争取的释放它们呢?
温馨提示:答案为网友推荐,仅供参考
第1个回答  2008-12-02
有点意思的问题。我一开始只是猜测,但写了个例子测试了下,发现我的猜测还是正确的。

在C里面无论是数组还是单个变量,他都可以看成是数组,单个变量其实就是长度为1的数组(可以这么理解吧),C中以\0来表示一个数组结束(但有一点要弄明白,C不检查数组长度,虽然它能得到数组长度).所以你的问题好回答了。首先它们都是数组,只不过单个变量的长度为1,其次我释放的时候碰到\0就结束就可以了。下面是我一个测试的例子,应该不难懂。

[root@liumengli MSG]# cat test.c (如果不懂shell这里是注释,cat是现实test.c文件的内容)
#include "stdio.h"

int main() {
int * a = (int *)malloc(sizeof(int));
int * b = (int *)malloc(10*sizeof(int));
printf("%ld, %ld\n", a, b);
if(a[1] == '\0')
printf("a[1] is end\n");
if(b[10] == '\0')
printf("b[10] is end\n");
free(a);
free(b);
}
[root@liumengli MSG]# gcc test.c -o test(gcc是编译器,相当于tc,当然比TC要强大点)
[root@liumengli MSG]# ./test
134520840, 134520856
a[1] is end
b[10] is end
[root@liumengli MSG]#

这只是最简单的理解,我想真正的内存释放完全没有这么简单,内存都是以页为单位的(linux中一页大小是4K),就是说要分配就分配就分配一页,要释放就释放一页,没有分一个数组这种说法,我打印过a和b的地址,他们逻辑地址中反映他们应该是处于同一页的,我估计free应该是减少了页的共享计数,而没有释放内存页面,真正的释放应该是在进程结束后,操作系统检查该页的共享计数为0的时候,将该页标记为没有使用。(当然个人理解,当初看释放页面代码的时候没太明白).
第2个回答  2008-12-02
p2依然是分配好的内存首地址,可以正确释放,你只是用数组下标来操作指针,本质上p2没有任何改变.
为什么可以正确的释放正确大小的地址,有的编译器会这样操作,malloc会在首地址前8个字节的高4存放page id,低4存放size,free可以从这里取到内存的大小,依赖编译器的不同实现方法不同,仅供你参考。
第3个回答  2008-12-02
假设
p1 = 0x12400;
p2 = 0x12800;
那么 0x12400,0x12800 这两个值程序是有记录,有标识的

free( (void*)0x12400 ); 这样写是可以的!
第4个回答  2020-06-03
1、free函数:
原型:void
free(void
*ptr);
功能:释放malloc(或calloc、realloc)函数给指针变量分配的动态内存;
头文件:malloc.h或stdlib.h;
2、为了避免释放已经释放了内存的指针内存,或没有释放内存,在c语言中最好是在定义指针时赋初值null,释放后立即赋null,释放时检查指针值再决定释放就避免释放错误了,例如:
int *a = null
int *b = (int*) malloc(sizeof(int) * 10);
a= b;
/* 执行大量操作后 */
if(a != null) {free(a);a=null;}
if(b != null) {free(b);b=null;}

相关了解……

你可能感兴趣的内容

本站内容来自于网友发表,不代表本站立场,仅表示其个人看法,不对其真实性、正确性、有效性作任何的担保
相关事宜请发邮件给我们
© 非常风气网