sqlserver關(guān)于分頁存儲過程的優(yōu)化【讓數(shù)據(jù)庫按我們的意思執(zhí)行查詢計劃】
更新時間:2011年08月28日 22:08:04 作者:
先來對比兩段分頁SQL,假設(shè)條件:news表有15萬記錄,NewsTypeId=10有9萬記錄,當(dāng)前查詢NewsTypeID=10。那么,你會認(rèn)為哪個SQL效率會高呢?
復(fù)制代碼 代碼如下:
--代碼一DECLARE @cc INT
SELECT NewsId,ROW_NUMBER() OVER(ORDER BY SortNum DESC) AS RowIndex INTO #tb FROM news WITH(NOLOCK) WHERE NewsTypeId=@NewsTypeId AND IsShow=1
SET @cc = @@ROWCOUNT
SELECT n.* FROM news AS n WITH(NOLOCK), #tb As t WHERE t.RowIndex>@PageIndex*@PageSize AND t.RowIndex<=(@PageIndex+1)*@PageSize AND t.newsid=n.newsid
SELECT @cc
DROP TABLE #tb
復(fù)制代碼 代碼如下:
--代碼二
DECLARE @cc INT
SELECT NewsId,ROW_NUMBER() OVER(ORDER BY SortNum DESC) AS RowIndex INTO #tb FROM news WITH(NOLOCK) WHERE NewsTypeId=@NewsTypeId AND IsShow=1
SET @cc = @@ROWCOUNT
SELECT NewsId INTO #tb2 FROM #tb As t WHERE t.RowIndex>@PageIndex*@PageSize AND t.RowIndex<=(@PageIndex+1)*@PageSize
SELECT * FROM news WITH(NOLOCK) WHERE NewsId IN (SELECT * FROM #tb2)
SELECT @cc
DROP TABLE #tb
DROP TABLE #tb2
答案是代碼二遠(yuǎn)遠(yuǎn)高于代碼一。在代碼一中加粗代碼的操作會引起整表掃描,因為數(shù)據(jù)庫引擎在認(rèn)為WHERE表達(dá)式中滿足條件記錄大于一定閥值的時候,就不再去進(jìn)行查詢優(yōu)化,而直接使用表掃描??磮?zhí)行信息,:
表 'news'。掃描計數(shù) 1,邏輯讀取 342 次,物理讀取 0 次,預(yù)讀 0 次,lob 邏輯讀取 0 次,lob 物理讀取 0 次,lob 預(yù)讀 0 次。
(98361 行受影響)
(1 行受影響)
(40 行受影響)
表 '#tb________________________________________00000004C024'。掃描計數(shù) 1,邏輯讀取 257 次,物理讀取 0 次,預(yù)讀 0 次,lob 邏輯讀取 0 次,lob 物理讀取 0 次,lob 預(yù)讀 0 次。
表 'news'。掃描計數(shù) 1,邏輯讀取 2805 次,物理讀取 0 次,預(yù)讀 235 次,lob 邏輯讀取 0 次,lob 物理讀取 0 次,lob 預(yù)讀 0 次。
(1 行受影響)
(1 行受影響)
原本,我想的執(zhí)行計劃,加粗部分的代碼應(yīng)該是聚焦索引查找,這樣性能就提高很多。看代碼二:
表 'news'。掃描計數(shù) 1,邏輯讀取 342 次,物理讀取 0 次,預(yù)讀 0 次,lob 邏輯讀取 0 次,lob 物理讀取 0 次,lob 預(yù)讀 0 次。
(98361 行受影響)
(1 行受影響)
表 '#tb____________________________________00000004BEEF'。掃描計數(shù) 1,邏輯讀取 257 次,物理讀取 0 次,預(yù)讀 0 次,lob 邏輯讀取 0 次,lob 物理讀取 0 次,lob 預(yù)讀 0 次。
(40 行受影響)
(1 行受影響)
(40 行受影響)
表 'news'。掃描計數(shù) 0,邏輯讀取 131 次,物理讀取 0 次,預(yù)讀 0 次,lob 邏輯讀取 0 次,lob 物理讀取 0 次,lob 預(yù)讀 0 次。
表 '#tb2___________________________________00000004BEF0'。掃描計數(shù) 1,邏輯讀取 2 次,物理讀取 0 次,預(yù)讀 0 次,lob 邏輯讀取 0 次,lob 物理讀取 0 次,lob 預(yù)讀 0 次。
(1 行受影響)
(1 行受影響)
很明顯,代碼二與代碼一中的IO操作數(shù)大大降低。且代碼一隨著@PageIndex越來越大,效率會越來越低;但代碼二的效率不會隨@PageIndex變化而改變。
您可能感興趣的文章:
- sqlserver數(shù)據(jù)庫規(guī)模膨脹太大怎么優(yōu)化
- SQL Server 聚焦存儲過程性能優(yōu)化、數(shù)據(jù)壓縮和頁壓縮提高IO性能方法(一)
- 日常收集整理SqlServer數(shù)據(jù)庫優(yōu)化經(jīng)驗和注意事項
- SQL server 2008 數(shù)據(jù)庫優(yōu)化常用腳本
- sqlserver數(shù)據(jù)庫優(yōu)化解析(圖文剖析)
- SQL Server數(shù)據(jù)庫的高性能優(yōu)化經(jīng)驗總結(jié)
- 開啟SQLSERVER數(shù)據(jù)庫緩存依賴優(yōu)化網(wǎng)站性能
- SQL Server 數(shù)據(jù)庫優(yōu)化
- SQL Server數(shù)據(jù)庫性能優(yōu)化技術(shù)
- SQL Server 數(shù)據(jù)太多優(yōu)化的方法
相關(guān)文章
SQL Server內(nèi)存遭遇操作系統(tǒng)進(jìn)程壓榨案例分析
最近一臺DB服務(wù)器偶爾出現(xiàn)CPU報警,我的郵件報警閾值設(shè)置的是15%,開始時沒當(dāng)回事,以為是有什么統(tǒng)計類的查詢,后來越來越頻繁2014-03-03
SQL參數(shù)化查詢的另一個理由 命中執(zhí)行計劃
為了提高數(shù)據(jù)庫運(yùn)行的效率,我們需要盡可能的命中執(zhí)行計劃,這樣就可以節(jié)省運(yùn)行時間2012-08-08
SQL Server中將查詢結(jié)果轉(zhuǎn)換為Json格式腳本分享
這篇文章主要介紹了SQL Server中將查詢結(jié)果轉(zhuǎn)換為Json格式腳本分享,本文直接給出實現(xiàn)代碼,需要的朋友可以參考下2015-02-02
SqlServer實現(xiàn)類似Oracle的before觸發(fā)器示例
本節(jié)主要介紹了SqlServer如何實現(xiàn)類似Oracle的before觸發(fā)器,需要的朋友可以參考下2014-08-08
SQL Server本地時間和UTC時間的相互轉(zhuǎn)換實現(xiàn)代碼
SQL Server 本地時間和UTC時間的相互轉(zhuǎn)換的代碼,需要的朋友可以參考下。2011-07-07

