c-11 堆内存

概述

c语言中,堆区可以自由被开发者掌控。高度的自由也需要带来高额的管理成本,如申请后需要手动释放,本文是笔者学习堆区的笔记。

malloc和free

malloc:

void *malloc(
   size_t size
);

参数:
size申请堆内存大小。

返回:
成功返回内存地址,失败返回NULL

macllo内存格式:

在这里插入图片描述

(注意博主在vs2015中内存结构如上图所示,不同编译器有所不同)

堆类别决定系统如何管理这个块内存。

#include<stdlib.h>
int main(void) {

	char *intP = (char*)malloc(sizeof(char) * 2);
	int *intP2 = (int*)malloc(sizeof(int) * 2);
	free(intP);
	free(intP2);
}

我们首先查看intP内存结构图:
在这里插入图片描述

上图堆类别写错了,这里1是指这个堆是正常类别的堆。

我们可以从右侧观察窗口看到intP保存的内存地址就是内存堆栈中实际使用地址即0x010e8a78。而补充的对地址和实际使用地址相差0x20大小。

我们查看一下intP2 内存的地址为0x010e4950intP指向的下一个对地址为0x010E4930,当0x010E4930+0x20=intP2
下图为intP2内存结构图:
在这里插入图片描述

可以看到intP2上一个堆地址加上20偏移正好就是IntP

如果开发者想在堆中添加调试信息请用如下api:

void *_malloc_dbg(
   size_t size,
   int blockType,
   const char *filename,
   int linenumber
);

blockType是对堆的类别
枚举如下:
#define _FREE_BLOCK 0
#define _NORMAL_BLOCK 1
#define _CRT_BLOCK 2
#define _IGNORE_BLOCK 3
#define _CLIENT_BLOCK 4
#define _MAX_BLOCKS 5
#define _UNKNOWN_BLOCK (-1)

举例说明:

#include<stdlib.h>
#include<crtdbg.h>

int main(void) {
	char *intP = (char*)_malloc_dbg(sizeof(char) * 2,1,__FILE__,__LINE__);
	free(intP);
}

在这里插入图片描述
我们跳转到对应的常量池地址
在这里插入图片描述

free:

void free(
   void *memblock
);

释放memblock指向的内存。

我们看下free释放前后的区别:

释放前:
在这里插入图片描述
释放后:
在这里插入图片描述
同时修改上下级堆链表的内存,这里就不做讲解了。(堆内存结构会存储一个上一个堆地址和下一个堆地址,当删除一个堆的时候会进行链表删除操作)

calloc和realloc

calloc

void *calloc(
   size_t number,
   size_t size
);

申请number*size的内存大小


#include<stdlib.h>
#include<crtdbg.h>
#include<stdio.h>
int main(void) {
	int *p = (int *)calloc(1, sizeof(int));
	free(p);
	getchar();

}

realloc
重新给指向的地址分配新的大小。


#include<stdlib.h>
#include<crtdbg.h>
#include<stdio.h>
int main(void) {

	char* intP = (char*)malloc(4);
	char *p = (char *)realloc(intP, 3);
	free(p);
	getchar();

}

注意realloc会拷贝旧内存数据到新内存地址,而后释放旧堆。并且如果新生申请内存大小大于旧的大小。不管是缩小还是放大新堆都容易引起内存碎片问题

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值