原文:SQL Server :理解GAM和SGAM页

我们知道SQL Server在8K 的页里存储数据。分区就是物理上连续的8个页。当我们创建一个数据库,数据文件会被逻辑分为页和区,当用户对象创建时,页会分配给它用来存储数据。GAM(Global Allocation Map)和SGAM(Shared Global Allocation Map)页用来跟踪SQL Server里空间分配情况。这里我们会一起讨论下SQL Server的空间分配,还有GAM和SGAM怎么帮助我们分配空间。

在SQL Server里有2类区:

统一区(Uniform Extent) :区属于一个用户对象。这些区的所有8页归一个对象所有。

混合区(Mixed Extent) :区属于各个用户对象。即区里的每个页都可以属于不同用户对象。

为了更好的管理空间分配,如果一个表或索引大小小于8页(即64k),SQL Server会分配混合区的页,而不是统一区的页。

我们在SQL Server里验证下。

新建一个表(这个表刚好一条记录一个页面),并插入26条记录,并通过DBCC IND查看这个表的相关页面:

 USE InternalStorageFormat
GO IF EXISTS ( SELECT *
FROM sysobjects
WHERE id = OBJECT_ID(N'[dbo].[TestSpaceAllocation]')
AND OBJECTPROPERTY(id, N'IsUserTable') = 1 )
DROP TABLE dbo.TestSpaceAllocation CREATE TABLE TestSpaceAllocation(
Name CHAR(8000)
)
GO INSERT INTO TestSpaceAllocation VALUES('Woody')
GO 26 DBCC IND('InternalStorageFormat','TestSpaceAllocation',1)

从上图我们可以清楚的看到,绿色区域的第一个8页不属于同个区(混合区),因为页面号不连续,204余206之间有缺口,207余94752之间也有缺口。接下来蓝色红色区域是属于同个区(统一区),因为它们的页面号是连续的。当我们以碎片级别来看待这个情况时,可以发现表越小,碎片越高。即使你用索引重建,这个高碎片也不会减少。这个背后的原因就是SQL Server分配新的表或索引对象时,总是首先从混合区分配空间。
SQL Server为新表或索引从混合区开始分配页。一旦表增长超过8页。SQL Server需要从统一区分配页。当表或索引为新的或修改的数据需要更多的容纳空间时,SQL Server需要这些表或索引分配页。如果表或索引的大小小于8页。SQL Sever需要从混合区给它们分配空间。如果大小超过8页,SQL Server需要从统一区分配页。SQL使用2类不同的页来更好管理这个分配操作。

全局分配映射表(GAM: Global Allocation Map Pages) :GAM页记录哪些些区已被使用分配。对于每个区,GAM都有一个位。如果这个位是1,表示对应的区是空闲可用的。如果这个位是0,表示对应区被统一区或混合区使用。一个GAM页可以保存64000个区的使用信息。这就是说,一个GAM可以保存近4G(64000 * 8 * 8/ 1024)数据文件的使用信息。简单来说,一个7G的数据文件会有2个GAM页。
共享全局分配映射表(SGAM: Shared Global Allocation Map Pages) :SGAM页记录哪些区已被作为混合区使用并至少有一个可用的空闲页。对于每个区,SGAM都有一个位。如果这个位是1,表示对应的区作为混合区使用并至少有一个可用的空闲页。如果这个位是0,表示这个区既没被混合区使用(作为统一区),或这个区的所有页都作为混合区使用了。一个SGAM页可以保存64000个区的使用信息。这就是说,一个SGAM可以保存近4G(64000 * 8 * 8/ 1024)数据文件的使用信息。简单来说,一个7G的数据文件会有2个SGAM页。

GAM和SGAM页帮助数据库引擎进行区管理。分配一个区,数据库引擎查找标记1的GAM页,然后标记为0。如果那个区是作为混合区分配,它会在SGAM页把对应区的标记为1。如果那个区是作为统一区分配,那就没有必要在SGAM里修改对应位标记。找一个有空页的混合区,数据库引擎在SGAM页查找标记为1的位。如果没找到,数据文件已经满了。解除一个区分配,数据库引擎会把对应GAM页里对应位设置为1,SGAM页里对应标记设置为0。

在每个数据文件里,第3个页(页号2,页号从0开始)是GAM页,第4个页(页号3,页号从0开始)是SGAM页。第1个页(页号0)是文件头(file header),第2个页(页号1)是PFS(Page Free Space)页。我们可以使用DBCC PAGE命令查看GAM和SGAM页。

我们在AdventureWorks2008R2数据库里验证下:

 USE AdventureWorks2008R2

 DBCC TRACEON(3604)
GO
DBCC page('AdventureWorks2008R2',1,2,3)

输出的结果最后一个部分:

第1行表示,在页0到页23112之间的区都已经被分配,也就是说页号从0到23129的页都被分配。

第2行表示,在页23120到页25072之间的区都没被分配,也就是说页号从22120到页25079的页都未被分配。

我们一起来看看分配的页23112和未分配的页23120在页头分配信息里的GAM分配情况。

 DBCC TRACEON(3604)
GO
DBCC page('AdventureWorks2008R2',1,23112,1)

 DBCC TRACEON(3604)
GO
DBCC page('AdventureWorks2008R2',1,23120,1)

可以看到在GAM页的分配信息和在对应页里页头的分配信息(Allocation Statu)是一致的。

我们来看看SGAM页的分配情况:

 DBCC TRACEON(3604)
GO
DBCC page('AdventureWorks2008R2',1,3,3)

第1行表示,在页0到页11752之间的区都已经未被分配,也就是说这些区没被分配,或者是统一区,或者是没有空页的混合区,这里应该是统一区。

第2行表示,自页11760的区开始是混合区,并且至少有1个可用的页。

SQL Server :理解GAM和SGAM页的更多相关文章

  1. Sql Server 中 GAM、SGAM、PAM、IAM、DCM 和 BCM 的详解与区别

    Sql Server 中 GAM.SGAM.PAM.IAM.DCM 和 BCM 的详解与区别   GAM.SGAM.PAM.IAM.DCM 和 BCM 都是 SQL Server 中用来管理空间分配的 ...

  2. SQL Server 存储(3/8):理解GAM和SGAM页

    我们知道SQL Server在8K 的页里存储数据.分区就是物理上连续的8个页.当我们创建一个数据库,数据文件会被逻辑分为页和区,当用户对象创建时,页会分配给它用来存储数据.GAM(Global Al ...

  3. 在SQL Server里如何进行数据页级别的恢复

    在SQL Server里如何进行页级别的恢复 关键词:数据页修复 在今天的文章里我想谈下每个DBA应该知道的一个重要话题:在SQL Server里如何进行页级别还原操作.假设在SQL Server里你 ...

  4. SQL Server 存储(8/8):理解数据文件结构

    这段时间谈了很多页,现在我们可以看下这些页在数据文件里是如何组织的. 我们都已经知道,SQL Server把数据文件分成8k的页,页是IO的最小操作单位.SQL Server把数据文件里的第1页标记为 ...

  5. SQL Server性能优化(7)理解数据库文件组织

    一.基本单位"页"     SQL Server是用8KB的页来存储数据.物理I/O操作也是在页级执行.页的种类有很多,具体参考(MSDN).我们关注更多的是数据页的结构,包括三部 ...

  6. SQL Server :理解DCM页

    原文:SQL Server :理解DCM页 我们已经讨论了各种不同的页,包括数据页.GAM与SGAM页.PFS页,还有IAM页.今天我们来看下差异变更页(Differential Change Map ...

  7. SQL Server :理解IAM 页

    原文:SQL Server :理解IAM 页 在以前的文章里,我们讨论了数据页,GAM和SGAM,还有PFS页.今天我们一起来讨论下索引分配映射(Index Allocation Map:IAM)页. ...

  8. SQL Server :理解Page Free Space (PFS) 页

    原文:SQL Server :理解Page Free Space (PFS) 页 我们已经讨论了GAM与SGAM页,数据页(Data Page) ,现在我们来看下页面自由空间页(Page Free S ...

  9. [转帖]真TM长的:SQL Server 2008存储结构——GAM和SGAM、PFS结构、IAM结构、DCM&BCM

    谈到GAM和SGAM,我们不得不从数据库的页和区说起. https://blog.csdn.net/snowfoxmonitor/article/details/49991015 一个数据库由用户定义 ...

随机推荐

  1. csdn的登录框好难看

    不好意思说实话了,新的登陆框样式挺难看的,那种橙不明朗,介于黄和橙之间,跟整个网站主色调红和黑很不搭.不过,倒是有点跟风Win8平实的style,但是比Win8更简陋了点. tooltip要不加都不加 ...

  2. c++中虚函数和纯虚函数定义

    只有用virtual声明类的成员函数,使之成为虚函数,不能将类外的普通函数声明为虚函数.因为虚函数的作用是允许在派生类中对基类的虚函数重新定义.所以虚函数只能用于类的继承层次结构中. 一个成员函数被声 ...

  3. ZOJ 1859 Matrix Searching(二维线段树)

    http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemId=1859 Matrix Searching Time Limit: 10 Seco ...

  4. php中empty()、isset()、is_null()和变量本身的布尔判断区别(转)

    在php脚本中,我们经常要去判断一个变量是否已定义或者是否为空,就需要用到这些函数empty().isset().is_null()和其本身作为参数,下面小段程序做个简要比较 <?php//预定 ...

  5. eclipse中我要同时看两个console

    eclipse中我要同时看两个console 有一个按钮“New Console View”,可以让你再建一个Console,还有一个按钮“Display Selected Console”,可以在两 ...

  6. KFC - About KFC - Quality Assurance

    KFC - About KFC - Quality Assurance Restaurant Quality The main attributes for KFC restaurant excell ...

  7. IE常见的CSS的BUG(二)

    之前介绍过IE浏览器的几种BUG解决的方法,今天我们继续研究IE的BUG.尽管IE6即将被淘汰,但是了解这些也对将来解决问题也是有一定帮助的.好了,闲话不多说,咱们继续看IE的BUG. 1.IE6下P ...

  8. spring配置日志

    原文:http://blog.csdn.net/xiejx618/article/details/41698913 参考:http://spring.io/blog/2009/12/04/loggin ...

  9. hdu2861(递推)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2861 题意:n个板凳有m个人坐,求刚好将序列分成k段的方式. 分析: a[n][m][k]=a[n-1 ...

  10. linux centos 卸载jdk

    1.先看看OpenJDK的安装包 $ rpm -qa |grep java tzdata-java-2013b-1.el6.noarch java-1.6.0-openjdk-1.6.0.0-1.61 ...