堆表空间管理
发布日期:2021-10-17 00:06:12 浏览次数:20 分类:技术文章

本文共 2019 字,大约阅读时间需要 6 分钟。

在SQL Server中,堆表是指没有创建聚集索引的表,其存储空间由PFS,IAM等系统页来跟踪,PFS使用1Byte,表示一个page中空间的使用情况。BTree结构的存储空间是有序的,当向BTree结构中插入新的数据行时,SQL Server按照键值该数据行插入到特定的位置上,以保证BTree结构是有序的;当删除一个Page中的所有数据行之后,SQL Server会将该Empty Page释放,其他对象可以使用该Page。堆表的空间管理,和BTree结构有很大的不同。

1,读取堆表的数据

当需要查询堆表的数据时,SQL Server只能使用表扫描(Table Scan)访问堆表数据。表扫描意味着SQL Server会将访问堆表的所有数据行,以检查该数据行是否满足查询条件。

2,向堆表中插入数据

SQL Server可能将新的数据行插入到表结构的任何page中。在向堆表中插入数据行时,SQL Server扫描PFS系统页,查看堆表的存储空间,只要发现任何一个page有足够的空闲空间能够容纳新的数据行,SQL Server就将数据插入到该位置。如果该Page的存储数据行分布低比较零散,SQL Server会重新组织该数据页上现有数据行的存储,以腾挪出连续的空闲空间,存储新的数据行。

如果已分配的数据页没有足够的空闲空间容纳新的数据行,那么SQL Server会分配新的extent,以存储数据。

3,从堆表中删除数据

当从heap中删除数据行时,SQL Server 2012不会自动组织Page的存储空间,直到插入新的数据行时,SQL Server才会收缩Page中零散的空间,腾挪出连续的空闲空间,以存储新的数据行。如果将Page的所有数据行都删除,SQL Server不会将empty pages的存储空间释放,这部分空间仍然被堆表占用,不能被其他对象使用。

In additin to space on pages, not being reclaimed, empty pages in heaps frequently can not be reclaimed. Even if you delete all the rows from a heap, sql server does not mark the mepty pages as unallocated, so the space is not available for other objects to uses.

在执行删除操作使时,如果使用with(tablock)申请表锁,那么SQL Server在删除数据行时,将释放Empty Page的存储空间。

如果堆表已经存在大量的空闲空间未被释放,有两种方式来解决:

  • 执行alter table rebuild命令,重新创建堆表空间,SQL Server将为堆表分配新的存储空间,而释放原有的存储空间,新的存储空间是密集存储的;
  • 在堆表上,创建聚集index,将堆表转换为BTree,使用BTree结构管理表空间

4,更新堆表的数据

在更新堆表数据时,如果数据行长度增加,导致数据页不足以容纳更新之后的数据行,那么SQL Server将该数据行移动到其他Data Page上,在原有的Data Page上设置一个Forward Pointer,指向数据行移动之后的物理位置,这样做的好处是,堆表数据的更新不会影响nonclustered index。

如果数据行再次移动,那么Forward Pointer会执行新的物理位置,Forward Pointer会指向数据行的最新的物理位置。如果数据行更新之后,原有的存储空间能够容纳,那么SQL Server移除Forward Pointer,将数据行移动到原有的物理位置上。

Forward Pointer利于堆表数据的更新,但是,不利于堆表数据的查询。SQL Server通过Forward Pointer获取数据行的物理位置,再路由到相应的物理位置去读取数据行的数据,额外增加一次Disk的查询操作。

移除Forward Pointer的操作:

  • 收缩数据文件,执行dbcc shrinkfile命令,SQL Server将移除堆表的所有Forward Pointer
  • 在堆表上创建clustered index
  • 将Forward Pointer指向的数据行删除
  • 在执行更新命令时,数据行宽度变窄,SQL Server移除Forward Pointer,将数据行移动到原有的物理位置上
  • 重建堆表,执行alter table rebuild命令,重新分配堆表的存储空间

5,查看堆表中Forward Pointer的数量

在SQL Server中,Index ID是0,表示堆表结构;Index ID是1,表示Clustered Index。

转载地址:https://blog.csdn.net/sulan2131/article/details/69099227 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!

上一篇:搭建wamp环境,数据库基础知识
下一篇:Url Rewrite 再说Url 重写

发表评论

最新留言

关注你微信了!
[***.104.42.241]2024年04月18日 17时55分28秒

关于作者

    喝酒易醉,品茶养心,人生如梦,品茶悟道,何以解忧?唯有杜康!
-- 愿君每日到此一游!

推荐文章

转:【答学员问】有什么经验教训,是你在面试很多次之后才知道的? 2019-04-27
消息队列:解耦、异步、削峰,现有MQ对比以及新手入门该如何选择MQ? 2019-04-27
【奇技淫巧】-- 三角形最小路径和 2019-04-27
【小技巧】argc和argv的用法 2019-04-27
学不下去了怎么办? 2019-04-27
二叉树的前中后序遍历(迭代法)(带动画) 2019-04-27
【小技巧】【XShell】【Xftp】Windows桌面与Linux虚拟机互传文件 2019-04-27
【redis入门】Centos下安装redis 2019-04-27
【redis入门】redis安装后相关知识串讲 2019-04-27
【redis】来吧,展示一下redis 发布-订阅模式 2019-04-27
讲通C/C++预编译/条件编译指令 #ifdef,#ifndef,#endif,#define,… 2019-04-27
【redis6.0.6】redis源码慢慢学,慢慢看 -- 第二天:空间配置(zmalloc) 2019-04-27
当下热点词再学:redis缓存预热、更新、降级,限流 2019-04-27
【redis6.0.6】redis源码慢慢学,慢慢看 -- 第五天:adlist 2019-04-27
别抖,OK? 操作系统抖动现象、网络抖动与延迟、函数抖动之防抖与节流,串讲 2019-04-27
第六天:网络处理(anet部分)-- redis源码慢慢学,慢慢看【redis6.0.6】 2019-04-27
通过域名获取主机IP -- struct addrinfo 2019-04-27
【C++】算法集锦(8):从两数和问题拓展到一百数和问题 2019-04-27
【C++】算法集锦(9):背包问题 2019-04-27
【C++】算法集锦(10)通俗讲kmp算法 2019-04-27