堆结构

堆与栈的区别:

  1. 栈空间是在程序设计时已经规定好怎么使用,使用多少内存空间的。
  2. 堆是一种在程序运行时动态分配的内存。
  3. 堆是需要程序员自己通过malloc、new等函数自己申请的,根据程序的运行环境和申请的大小也有可能申请失败。
  4. 一般我们通过一个堆指针来使用所申请到的堆内存,进行读、写、释放等操作。
  5. 使用完成后需要把堆指针传给释放函数(free、delete)来回收这片内存,否则会造成内存泄漏。
堆的数据结构与管理策略

  • 堆块:堆区的内存按大小不同组织成堆块,以堆块为单位进行标识。一个堆块包括两个部分:块首和块身。块首是一个堆块头部的几个字节,用来标识这个堆块自身的信息,例如:大小、是否空闲;块身紧跟在块首后面,是分配给用户使用的数据区。

  • 堆管理系统所返回的指针一般指向块身的起始位置

  • 堆表:堆表一般位于堆区的起始位置,用于索引堆区中所有堆块的重要信息,堆表的数据结构决定了整个堆区的组织方式,是快速检索空闲块、保证堆分配效率的关键。现代操作系统的堆表往往不止一种数据结构。

在这里插入图片描述

堆的内存组织
  • 在Windows中,占用态的堆块被使用他的程序索引,而堆表只索引所有空闲态的堆块。其中,最重要的堆表有两种:空闲双向链表Freelist(简称 空表),和快速单向链表Lookaside(简称 快表)。
1. 空表

​ 空闲堆块的块首中包含一对重要的指针,这对指针用于将空闲堆块组织成双向链表。按照堆块的大小不同,空表总共被分成128条。

​ 堆区一开始的堆表区中有一个128项的指针数组,被称做空表索引。该数组的每一项包括两个指针,用于标识一条空表。

​ 空表索引的第二项(free[1])标识了堆中所有大小为8字节的空闲堆块,之后每个索引项递增8个字节,空闲堆块的大小 = 索引项(ID) 8(字节)*

​ 把空闲堆块按照大小链入不同的空表,可以方便堆管理系统高校检索指定大小的空闲堆块。空表索引的第一项比较特殊,这条双向链表链入了所有大于等于1024字节的堆块(小于512KB)。这些堆块按照大小依次排列。

在这里插入图片描述

空闲双向链表(Freelist)
2. 快表

​ 快表是Windows为了加速堆块分配而采用的一种堆表。这类单向链表从来不会发生堆块合并(其中的空闲块块首被设置为占用态,用来防止对快合并)。

​ 快表也有128条,组织结构与空表类似,只是其中的对快按照单链表组织。快表总是被初始化为空,而且每条快表最多只有4个节点,故很快就会被填满。

​ 堆中的操作可以分为堆块分配、堆块释放和堆块合并三种。其中“分配”和“释放”是在程序中提交申请和执行的,而堆块合并则是由堆块管理系统自动完成的。

在这里插入图片描述

快速单向链表(Lookaside)
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值