动态内存中的函数有malloc、calloc、realloc、free函数
头文件为# includ<malloc.h>
1、malloc函数,动态申请内存
calloc(元素数目*字节数)
malloc(n*sizeof(int) 含义为:申请了n个int型的字节数大小的内存,存放在堆里,地址连续,返回的是首地址。
int * p = (int *)malloc (n * sizeof (int) )含义为:定义了一个整型指针保存的是申请内存的首地址。红色的
部分int *表示的是强转的意思,因为malloc 申请的内存返回的是void型,也就是说需要多少个字节数,系统就分
配多大字节数的内存,并不关心是什么类型,当自己需要什么类型时就强转成什么类型。
申请失败的原因:申请内存过大,无法满足,返回空指针。若要防止申请失败可以这样做:
int *p = (int *)malloc(n*sizeof(int));//等同int p[n];
assert(p != NULL);
if(p == NULL)
{
return ;
}
2、calloc函数,动态申请内存,并赋值为0
calloc(元素数目,字节数)
int *arr = (int *)calloc(10,sizeof(int));
如下操作等同calloc
int *arr = (int *)malloc(10*sizeof(int));
for(int i=0;i<10;i++)
{
arr[i] = 0;
}
3、realloc函数,扩大或缩小申请的内存
realloc(以前指定的内存块,新的大小)
p = (int *)realloc(p,20*sizeof(int));
下面的代码等同realloc
int *q = (int *)malloc(20*sizeof(int));
for(i=0;i<10;i++)
{
q[i] = p[i];
}
p = q;
q = NULL;
4、free函数,释放内存,不释放则内存泄漏
free不需要长度是因为有头和尾信息
int *p1 = (int *)malloc(10*sizeof(int));
free(p1);//Show(p1,10);,
show函数使用时要给出长度信息,而free函数不需要是因为申请的内存,存放时是有头有尾,头部存放有长度size
信息, 尾部的作用是无缝粘合的作用。当使用free函数是会自动搜索头部信息得到长度的信息。
free崩溃的原因:
(1)越界.漏写sizeof或realloc第二个参数写错成新增的字节数
int main()
{
int *p = (int *)malloc(10*sizeof(int));
for(int i=0;i<=10;i++)
{
p[i] = 0;
}
free(p);
return 0;
}
(2)修改了指针的指向,p++找不到头中的长度信息
int main()
{
int *p = (int *)malloc(10*sizeof(int));
for(int i=0;i<10;i++)
{
*p = 0;
p++;
}
free(p);
return 0;
}
(3)重复释放同一段内存
int main()
{
int *p = (int *)malloc(10*sizeof(int));
for(int i=0;i<10;i++)
{
p[i] = i;
}
int *q = (int *)malloc(20*sizeof(int));
for(int i=0;i<10;i++)
{
q[i] = p[i];
}
free(p);
p = q;
q = NULL;
free(p);
free(q);
return 0;
}
(4)释放非动态内存
int main()
{
int arr[10];
free(arr);
return 0;
}
free能否释放完后同时至空,不能因为释放后变成了野指针,不能再次访问了。自己定义了一个Free函数来实现。同时说明了若free要具有此功能,使用起来就比较麻烦。
void Free(int **p)
{
free(*p);
*p = NULL;
}
int main()
{
int *p = (int *)malloc(20);
printf("%d\n",p);
//free(p);
Free(&p);
printf("%d\n",p);//使用free(p)后变为野指针
p = NULL;
free(p);
return 0;
}