malloc/calloc/realloc的区别–C语言
在许多的面试题中,malloc、calloc、realloc这三个经常出现;因此,今天在这里,总结了这三个函数的区别。
共同点
- 堆用于程序运行时动态内存分配,对是可以向上增长的。三个函数在运行时所分配的动态内存空间都在堆上
- 在程序运行结束时,需要手动释放空间
- 在调用函数时,都要进行强制类型的转化
- 在函数调用结束后(即内存分配结束后),要进行判空
- 三个函数都是C标准库里的函数,在运用是都必须调用**#include<stdlib.h>或者include<malloc.h>**
不同点
malloc
void *malloc( size_t size );
申请内存的空间大小需要手动去计算,eg:要申请20个int类型的空间:int* p1=(int*)malloc(20*sizeof(int));
申请后空间的值是随机值
注意:三个函数括号里的内存大小单位都是字节
calloc
void *calloc( size_t num, size_t size );
在申请内存空间时不用手动去计算,eg:要申请20个int类型的空间:int* p2=(int*)calloc(20, sizeof(int));
申请后将空间的值挨个初始化为0
#include <malloc.h>
void Test1()
{
int* p1 = (int*)malloc(sizeof(int)*5);
int* p2 = (int*)calloc(5, sizeof(int));
printf("malloc的分配值:");
for (int i = 0; i < 5; i++)
{
printf("%d ", *p1++);
}
printf("\n");
printf("calloc的分配值:");
for (int j = 0; j < 5; j++)
{
printf("%d ", *p2++);
}
}
编译结果:
既然calloc还自带初始化功能,那为什么我们平时用的较多的还是malloc呢?
原因是:calloc自带初始化功能,就使得它的运行效率较低;而malloc的效率较快,并且,将空间值初始化为0的作用并不大,很多程序在分配完内存空间后就会对空间进行赋值;所以说大家更愿意选择效率较快的malloc函数
realloc
void *realloc( void *memblock, size_t size );
用于对内存空间进行扩容:
如果原内存空间足够大,系统将会在原内存空间的后面直接扩容,并且直接返回原内存空间的地址
如果原内存空间不够,系统将会重新申请一块内存(大小:原来与现在的和),把原来空间的数据拷贝到新的空间,将原来的空间释放
代码:
void Test2()
{
int size = 2000;
int* p1 = (int*)malloc(size * sizeof(int));
int* p2 = (int*)realloc(p1,sizeof(int)*20);
printf("malloc的首地址:%x\n",p1);
printf("realloc的首地址:%x\n", p2);
}
编译结果:
代码:
void Test3()
{
int size = 2000;
int* p1 = (int*)malloc(20* sizeof(int));
int* p2 = (int*)realloc(p1,sizeof(int)*size);
printf("malloc的首地址:%x\n",p1);
printf("realloc的首地址:%x\n", p2);
}
编译结果:
注意:如果扩容后,内存空间比原来的空间还小,就会出现数据丢失的情况