《Microsoft Sql server 2008 Internals》读书笔记--第五章Table(4)
《Microsoft Sql server 2008 Internals》索引目錄:
《Microsoft Sql server 2008 Internal》讀書筆記--目錄索引
?
?
上篇我們主要學(xué)習(xí)了元數(shù)據(jù)(metadata)的存儲及利用目錄視圖來查詢這些信息,今天,我們繼續(xù)學(xué)習(xí)數(shù)據(jù)頁(Data Pages)。
?數(shù)據(jù)頁(Data pages)是包含已經(jīng)添加到數(shù)據(jù)庫的表中的用戶數(shù)據(jù)的結(jié)構(gòu)。正如前面所看到的,數(shù)據(jù)頁有三類,每類數(shù)據(jù)頁以不同的方式存儲數(shù)據(jù)。復(fù)習(xí)一下,分別是in-row data pages、row-overflow data pages和LOB data pages。與其它類型的page一樣,data pages也是固定的8K大小或8192 bytes。它由三類組件組成:the page Header,data rows和the row offset array,如下圖所示:
1、Page Header
正如上圖所示,每個data page (除去96 bytes,還有8096 bytes存放data,row overhead和row offset)。你可以使用下面的DBCC Page命令來查看。
2、Data Rows for in-Rows
?Page Header的下面是row data,單個數(shù)據(jù)行最大可以存放8060 bytes的in-row data,這就是以前數(shù)據(jù)行不能超過8060限制的原因!有些行也可以在獨立的頁面(pages)中存放row-overflow data和LOB數(shù)據(jù),存儲在一個給定的page變量中的行數(shù)取決于表結(jié)構(gòu)及數(shù)據(jù)被存放的結(jié)構(gòu)。一個擁有全部固定長度列的表每頁能存儲相同的行數(shù)。一個擁有可變長度列的表在頁中存放不同的行數(shù)以適應(yīng)數(shù)據(jù)的實際長度。保持行長度盡量短,允許更多的行以適應(yīng)頁面,減少了I/O,改善了高速緩存命中率(cache-hit ratio)。
因此,作為系統(tǒng)架構(gòu)師或數(shù)據(jù)庫Designer,實在有必要了解這些啊。邀月深有體會。呵呵。程序很爛,是后天的,但數(shù)據(jù)結(jié)構(gòu)不合理,那是先天的,兩者的殺傷力同樣驚人!
3、Row Offset Array
行偏移數(shù)組(row offset array) 是一個2-byte entries的塊(block),每個項說明對應(yīng)數(shù)據(jù)行在頁開始的偏移,每行(row)有一個兩字節(jié)的項。盡管這些字節(jié)不會和數(shù)據(jù)一起存儲在行中,它們能影響適應(yīng)page的行數(shù)。行偏移數(shù)組揭示了行在頁上的邏輯順序。比如,如果一個表有一個聚集索引,SQL Server按聚集索引鍵的順序存放數(shù)據(jù)。這并不意味著數(shù)據(jù)是物理按聚集索引鍵的順序存放,而是行偏移數(shù)組的Slot 0 指向聚集索引鍵序列的第一行(row),Slot 1 指向第二行,等等。當(dāng)我們要快速查看實際頁的時候,這些行的物理位置可能在頁的任何位置。
?檢查數(shù)據(jù)頁(Exampling Data Pages)
?DBCC page命令可以幫我們查詢:MSDN文檔中中沒有提供此命令,微軟真的很那個啊。語法為:
DBCC?PAGE?({dbid?|?dbname},filenum,pagenum[,printopt])其中,最后一個參數(shù)可以是0,1,2,3,默認(rèn)為0,有興趣的朋友可以比較下這個參數(shù)的區(qū)別。我們作個示例:
DBCC?traceON(3604)go
--查詢testdb數(shù)據(jù)庫的第一個文件的第157頁的數(shù)據(jù)頁
DBCC?PAGE?(testdb,1,157,1);
GO
查詢結(jié)果如下:
此外,還有更詳細的第X到第X行的數(shù)據(jù)顯示。更多信息,請查看:
?http://support.microsoft.com/?scid=kb%3Ben-us%3B83065&x=15&y=13http://blogs.msdn.com/sqlserverstorageengine/archive/2006/12/13/More-undocumented-fun_3A00_-DBCC-IND_2C00_-DBCC-PAGE_2C00_-and-off_2D00_row-columns.aspx
?http://support.microsoft.com/?scid=kb%3Ben-us%3B83065&x=8&y=12
查詢結(jié)果分為四部分:BUFFER、PAGE HEADER、DATA、和OFFSET TABLE(即真實的offset array) ,
? 注意,要想得到類似上圖的查詢的明細信息,必須選擇打開TRACEON開關(guān),語法為:
DBCC?traceON(3604)GO
關(guān)于DBCC TRACEON (Transact-SQL)的更多用法,請參考MSDN
http://msdn.microsoft.com/en-us/library/ms187329.aspx
比如你想得知系統(tǒng)硬件的相關(guān)信息,可以通過DBCC traceON(3205)打開跟蹤開關(guān)。
?
?數(shù)據(jù)行的結(jié)構(gòu)(the structure of data rows)
一個表的通用結(jié)構(gòu)如下圖所示:
?
?其中:狀態(tài)位A包含一個關(guān)于行的位圖信息。這個bits有如下含義:
??????Bit?0?Versioning?information;?in?SQL?Server?2008,?it's?always?0.??????Bits?1?through?3?Taken?as?a?3-bit?value,?0?indicates?a?primary?record,?1?indicates?a?forwarded?record,?2?indicates?a?forwarded?stub,?3?indicates?an?index?record,?4?indicates?a?blob?fragment,?5?indicates?a?ghost?index?record,?and?6?indicates?a?ghost?data?record.
??????Bit?4?Indicates?that?a?NULL?bitmap?exists;?in?SQL?Server?2008,?a?NULL?bitmap?is?always?present,?even?if?no?NULLs?are?allowed?in?any?column.
??????Bit?5?Indicates?that?variable-length?columns?exist?in?the?row.
??????Bits?6?Indicates?that?the?row?contains?versionings?information.
??????Bits?7?Not?used?in?SQL?Server?2008.
狀態(tài)位B字段中只使用一位,表示該記錄是一條備份轉(zhuǎn)發(fā)記錄。
下表顯示了表數(shù)據(jù)行的存儲信息:
| Status Bits A | TagA | 1 byte |
| Status Bits B (not used in SQL Server 2008) | TagB | 1 byte |
| Fixed-length size | Fsize | 2 bytes |
| Fixed-length data | Fdata | Fsize --4 |
| Number of columns | Ncol | 2 bytes |
| NULL bitmap(1 byte for each column in table; 1 indicates that the corresponding column is NULL) | Nullbits | Ceiling (Ncol / 8) |
| Number of variable-length columns | VarCount | 2 bytes |
| Variable column offset array | VarOffset | 2 * VarCount |
| Variable-length data | VarData | VarOff[VarCount] |
?
有趣的是,當(dāng)你創(chuàng)建一個表的時候,固定長度的列是先被存儲的,比如這樣一個語句
CREATE?TABLE?dbo.Demotable2010(????????????????int?PKID,not?null
???????????????emp_fname??varchar(10)???NOT?NULL,?
???????????????phone??????char(12)??????NOT?NULL,?
???????????????job_level??smallint??????NOT?NULL?
);
首先存儲的是pkid,再是phone,job_level,最后才是?emp_fname,因為它是可變長度的。
后一篇我們將繼續(xù)學(xué)習(xí)固定長度的行和可變長度的行的存儲。真累啊!
總結(jié)
以上是生活随笔為你收集整理的《Microsoft Sql server 2008 Internals》读书笔记--第五章Table(4)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Silverlight 解谜游戏 之十四
- 下一篇: BadRank