SQL Server 索引結構及其使用(二) 改善SQL語句第2/3頁
更新時間:2009年04月09日 00:38:23 作者:
很多人不知道SQL語句在SQL SERVER中是如何執(zhí)行的,他們擔心自己所寫的SQL語句會被SQL SERVER誤解。
5、盡量少用NOT
6、exists 和 in 的執(zhí)行效率是一樣的
很多資料上都顯示說,exists要比in的執(zhí)行效率要高,同時應盡可能的用not exists來代替not in。但事實上,我試驗了一下,發(fā)現(xiàn)二者無論是前面帶不帶not,二者之間的執(zhí)行效率都是一樣的。因為涉及子查詢,我們試驗這次用SQL SERVER自帶的pubs數(shù)據(jù)庫。運行前我們可以把SQL SERVER的statistics I/O狀態(tài)打開:
(1)select title,price from titles where title_id in (select title_id from sales where qty>30)
該句的執(zhí)行結果為:
表 ''sales''。掃描計數(shù) 18,邏輯讀 56 次,物理讀 0 次,預讀 0 次。
表 ''titles''。掃描計數(shù) 1,邏輯讀 2 次,物理讀 0 次,預讀 0 次。
(2)select title,price from titles
where exists (select * from sales
where sales.title_id=titles.title_id and qty>30)
第二句的執(zhí)行結果為:
表 ''sales''。掃描計數(shù) 18,邏輯讀 56 次,物理讀 0 次,預讀 0 次。
表 ''titles''。掃描計數(shù) 1,邏輯讀 2 次,物理讀 0 次,預讀 0 次。
我們從此可以看到用exists和用in的執(zhí)行效率是一樣的。
7、用函數(shù)charindex()和前面加通配符%的LIKE執(zhí)行效率一樣
前面,我們談到,如果在LIKE前面加上通配符%,那么將會引起全表掃描,所以其執(zhí)行效率是低下的。但有的資料介紹說,用函數(shù)charindex()來代替LIKE速度會有大的提升,經(jīng)我試驗,發(fā)現(xiàn)這種說明也是錯誤的:
select gid,title,fariqi,reader from tgongwen
where charindex(''刑偵支隊'',reader)>0 and fariqi>''2004-5-5''
用時:7秒,另外:掃描計數(shù) 4,邏輯讀 7155 次,物理讀 0 次,預讀 0 次。
select gid,title,fariqi,reader from tgongwen
where reader like ''%'' + ''刑偵支隊'' + ''%'' and fariqi>''2004-5-5''
用時:7秒,另外:掃描計數(shù) 4,邏輯讀 7155 次,物理讀 0 次,預讀 0 次。
8、union并不絕對比or的執(zhí)行效率高
我們前面已經(jīng)談到了在where子句中使用or會引起全表掃描,一般的,我所見過的資料都是推薦這里用union來代替or。事實證明,這種說法對于大部分都是適用的。
select gid,fariqi,neibuyonghu,reader,title from Tgongwen
where fariqi=''2004-9-16'' or gid>9990000
用時:68秒。掃描計數(shù) 1,邏輯讀 404008 次,物理讀 283 次,預讀 392163 次。
select gid,fariqi,neibuyonghu,reader,title from Tgongwen where fariqi=''2004-9-16''
union
select gid,fariqi,neibuyonghu,reader,title from Tgongwen where gid>9990000
用時:9秒。掃描計數(shù) 8,邏輯讀 67489 次,物理讀 216 次,預讀 7499 次。
看來,用union在通常情況下比用or的效率要高的多。
但經(jīng)過試驗,筆者發(fā)現(xiàn)如果or兩邊的查詢列是一樣的話,那么用union則反倒和用or的執(zhí)行速度差很多,雖然這里union掃描的是索引,而or掃描的是全表。
select gid,fariqi,neibuyonghu,reader,title from Tgongwen
where fariqi=''2004-9-16'' or fariqi=''2004-2-5''
用時:6423毫秒。掃描計數(shù) 2,邏輯讀 14726 次,物理讀 1 次,預讀 7176 次。
select gid,fariqi,neibuyonghu,reader,title from Tgongwen where fariqi=''2004-9-16''
union
select gid,fariqi,neibuyonghu,reader,title from Tgongwen where fariqi=''2004-2-5''
用時:11640毫秒。掃描計數(shù) 8,邏輯讀 14806 次,物理讀 108 次,預讀 1144 次。
9、字段提取要按照“需多少、提多少”的原則,避免“select *”
我們來做一個試驗:
select top 10000 gid,fariqi,reader,title from tgongwen order by gid desc
用時:4673毫秒
select top 10000 gid,fariqi,title from tgongwen order by gid desc
用時:1376毫秒
select top 10000 gid,fariqi from tgongwen order by gid desc
用時:80毫秒
由此看來,我們每少提取一個字段,數(shù)據(jù)的提取速度就會有相應的提升。提升的速度還要看您舍棄的字段的大小來判斷。
相關文章
SQLServer 2008 CDC功能實現(xiàn)數(shù)據(jù)變更捕獲腳本
這篇文章主要介紹了使用SQLServer 2008的CDC功能實現(xiàn)數(shù)據(jù)變更捕獲的腳本,大家參考使用2013-11-11
sql添加數(shù)據(jù)后返回受影響行數(shù)據(jù)
Inserted 表用于存儲 INSERT 和 UPDATE 語句所影響的行的副本。在一個插入或更新事務處理中,新建行被同時添加到 inserted 表和觸發(fā)器表中2011-11-11
SQL Server 性能調(diào)優(yōu)之查詢從20秒至2秒的處理方法
這篇文章主要介紹了SQL Server 性能調(diào)優(yōu)之查詢從20秒至2秒的處理方法,需要的朋友可以參考下2017-07-07
SQL Server誤區(qū)30日談 第30天 有關備份的30個誤區(qū)
備份不會導致對用戶對象加鎖,雖然備份對IO系統(tǒng)的負擔導致看起來阻塞了,但實際上不會。唯一的特例是當備份包含到那些最小日志操作涉及到的數(shù)據(jù)區(qū)需要被加鎖時,這個操作會阻塞CheckPoint,但DML操作永遠不會受到備份操作的阻塞2013-01-01
SQL Server簡單模式下誤刪除堆表記錄恢復方法(繞過頁眉校驗)
這篇主旨是揭示堆表的刪除記錄找回的原理,我所考慮的方面并不適用于每個人的每種情況,望大家見諒2013-01-01
實現(xiàn)按關健字模糊查詢,并按匹配度排序的SQL語句
SQL語句實現(xiàn)按關健字模糊查詢,并按匹配度排序2009-09-09

