mallco动态分配_malloc函数动态分配内存

这篇博客详细介绍了C语言中动态内存分配的概念,包括malloc函数的使用、动态分配内存的管理,以及如何通过calloc、realloc和free进行内存初始化、调整大小和释放。示例代码展示了动态分配浮点数数组的过程,以及如何避免内存错误。
摘要由CSDN通过智能技术生成

#include

#include //malloc free

#include //sleep

void main1(){

//int a[1024*1024*1000]; //数组只能处理小数量的数据

int num =100;

//int b[num]; 数组的大小必须明确,num是变量,随时可以变化

//数组内存这种分配机制就称为静态分配,数组使用完成后系统自动回收

//动态内存分配

/* malloc和free是C标准库中提供的两个函数,用以动态申请和释放内存,malloc()函数的基本调用格式为:

void *malloc( unsigned int size );

参数size是个无符号整型数,用户由此控制申请内存的大小,执行成功时,系统会为程序开辟一块大小为size个内存字节的区域,并将该区域的首地址返回,

用户可利用该地址管理并使用该块内存,如果申请失败(比如内存大小不够用),返回空指针NULL。

malloc()函数返回类型是void*,用其返回值对其他类型指针赋值时,必须进行显式转换。

size仅仅是申请字节的大小,并不管申请的内存块中存储的数据类型,因此,申请内存的长度须由程序员通过“长度×sizeof(类型)”的方式给出,举例来说:

int* p=(int*) malloc(5* sizeof(int) );

Free就是释放内存,例如free(p)

*/

//输入一个数字,并用float类型的数据初始化,形式:1.000,2.000 ... f

float f;

scanf("%f",&f);

void *pVoid = malloc(f * sizeof(float)); //malloc返回值是空指针

float *pFloat = (float *)pVoid;

//下标法

for (int i = 0; i < f; ++i) {

pFloat[i] =i+1;

printf("%f,%p \n",pFloat[i],&pFloat[i]);

}

//指针法

printf("\n\n\n");

float *p =pFloat;

int fInt = (int)f;

for ( int i = 0; p < pFloat + fInt; ++i,++p) {

// p < pFloat + fInt此处的条件要注意,既然循环了,就要用p去循环, PFloat是不变的,切忌写成 p < p + fInt,这样的话 < 两边的p就一起动了

*p = i+1;

printf("%f,%p \n",*p,p);

}

free(pVoid); //释放内存 pVoid是地址,只能free一次, NUll指针可以释放多次

}

void main2(){

float f =3.0f;

int a =(int) f;

printf("%d,%f",a,a); //3,0.000000 一个很小的整数,按照%f来解析,会打印出 0.0000000

}

void main4(){

int n;

scanf("%d",&n);

//double *pDouble = (double *)malloc(n * sizeof(double)); //malloc不会初始化

double *pDouble = (double *)calloc(n, sizeof(double)); //calloc自动初始化内存为0

for (double i = 0.0; i < n; ++i) {

pDouble[(int)i] =i+1.0; //i 强制转换成int

printf("%lf,%p\n",pDouble[(int)i],&pDouble[(int)i]);

}

}

void main5(){

int num;

printf("please input the size of array:\n");

scanf("%d",&num);

int *p = (int *)malloc(num * sizeof(int));

if(p==NULL)/*防错处理,看内存申请是否成功*/

{

printf("内存申请失败,退出");

return;

}

for (int i = 0; i < num; ++i) {

p[i] =i+1;

printf("%d,%p\n",p[i],&p[i]);

}

printf("if you want to rezize the array, please input a new number:\n");

int newNum;

scanf("%d",&newNum);

//为已经分配的内存重新分配空间并复制内容

// realloc()函数有两个参数:已分配的内存地址,重新分配的字节数

//void *realloc( void *ptr, size_t size )

int *newP = (int *) realloc((void *)p,newNum);

//重新分配newNum字节的内存,并根据p的地址把原来malloc分配的内容复制过来

printf("after realloc, p :%d,%p\n",*p,p); // p :1,00030E58

printf("after realloc, p+5 :%d,%p\n",*(p+5),p+5); // after realloc, p+5 :13643,006D0E6C

//似乎realloc后,没有自动释放掉p,但p的地址不变,只是所指向的类型为空指针

for (int i = num; i < newNum; ++i) { //注意因为前num个元素已经有realloc复制过来了,所以从num开始复制

newP[i] =i+1;

}

//打印新的分配的数组

for (int j = 0; j < newNum; ++j) {

printf("%d,%p\n",newP[j],&newP[j]);

}

free(p); //内存释放以后,指针的值(地址)不会变化,只是把类型取消了

free(newP);

}

/*

please input the size of array:

3

1,00020E58

2,00020E5C

3,00020E60

if you want to rezize the array, please input a new number:

6

1,00020E58 可以看到新分配的内存空间首地址是一样的,可以得知旧的p指针所指向的那片内存空间后面任有剩余未占用的空间,所以继续往后分配

2,00020E5C 如果旧指针p后面没有剩余空间了,就会另外找一片内存区域,重新分配,旧的空间就自动释放掉

3,00020E60

4,00020E64

5,00020E68

6,00020E6C*/

void main(){

int num;

printf("please input the size of array:\n");

scanf("%d",&num);

int *p = (int *)malloc(num * sizeof(int));

if(p==NULL)/*防错处理,看内存申请是否成功*/

{

printf("内存申请失败,退出");

return;

} else{

for (int i = 0; i < num; ++i) {

p[i] = i + 1;

printf("%d,%p\n", p[i], &p[i]);

}

printf(" before free :%p\n",p);

free(p); //free 前后p的地址不会发生改变

printf("after free :%p\n",p);

p=NULL; //软件工程规范,释放指针后要置为NULL,可以规避释放后再次引用和反复释放的问题

printf("after free p[2]:%d\n",p[2]); //free之后,再次引用p[2]会出现垃圾数据,会报错

}

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值