校园春色亚洲色图_亚洲视频分类_中文字幕精品一区二区精品_麻豆一区区三区四区产品精品蜜桃

主頁 > 知識庫 > 在SQL SERVER中導致索引查找變成索引掃描的問題分析

在SQL SERVER中導致索引查找變成索引掃描的問題分析

熱門標簽:地圖標注跑線下市場 濮陽清豐400開頭的電話申請 真3地圖標注 南京怎么申請400這種電話 樂昌電話機器人 疫情時期電話機器人 臺灣外呼系統軟件 南通智能外呼系統怎么樣 地圖標注可以編輯地名嗎

SQL Server 中什么情況會導致其執行計劃從索引查找(Index Seek)變成索引掃描(Index Scan)呢? 下面從幾個方面結合上下文具體場景做了下測試、總結、歸納。

1:隱式轉換會導致執行計劃從索引查找(Index Seek)變為索引掃描(Index Scan)

Implicit Conversion will cause index scan instead of index seek. While implicit conversions occur in SQL Server to allow data evaluations against different data types, they can introduce performance problems for specific data type conversions that result in an index scan occurring during the execution.  Good design practices and code reviews can easily prevent implicit conversion issues from ever occurring in your design or workload. 

如下示例,AdventureWorks2014數據庫的HumanResources.Employee表,由于NationalIDNumber字段類型為NVARCHAR,下面SQL發生了隱式轉換,導致其走索引掃描(Index Scan)

SELECT NationalIDNumber, LoginID 
FROM HumanResources.Employee 
WHERE NationalIDNumber = 112457891 

我們可以通過兩種方式避免SQL做隱式轉換:

    1:確保比較的兩者具有相同的數據類型。

    2:使用強制轉換(explicit conversion)方式。

我們通過確保比較的兩者數據類型相同后,就可以讓SQL走索引查找(Index Seek),如下所示

SELECT nationalidnumber,
    loginid
FROM  humanresources.employee
WHERE nationalidnumber = N'112457891' 

注意:并不是所有的隱式轉換都會導致索引查找(Index Seek)變成索引掃描(Index Scan),Implicit Conversions that cause Index Scans 博客里面介紹了那些數據類型之間的隱式轉換才會導致索引掃描(Index Scan)。如下圖所示,在此不做過多介紹。

避免隱式轉換的一些措施與方法

    1:良好的設計和代碼規范(前期)

    2:對發布腳本進行Rreview(中期)

    3:通過腳本查詢隱式轉換的SQL(后期)

下面是在數據庫從執行計劃中搜索隱式轉換的SQL語句

SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED
DECLARE @dbname SYSNAME 
SET @dbname = QUOTENAME(DB_NAME());
WITH XMLNAMESPACES 
  (DEFAULT 'http://schemas.microsoft.com/sqlserver/2004/07/showplan') 
SELECT 
  stmt.value('(@StatementText)[1]', 'varchar(max)'), 
  t.value('(ScalarOperator/Identifier/ColumnReference/@Schema)[1]', 'varchar(128)'), 
  t.value('(ScalarOperator/Identifier/ColumnReference/@Table)[1]', 'varchar(128)'), 
  t.value('(ScalarOperator/Identifier/ColumnReference/@Column)[1]', 'varchar(128)'), 
  ic.DATA_TYPE AS ConvertFrom, 
  ic.CHARACTER_MAXIMUM_LENGTH AS ConvertFromLength, 
  t.value('(@DataType)[1]', 'varchar(128)') AS ConvertTo, 
  t.value('(@Length)[1]', 'int') AS ConvertToLength, 
  query_plan 
FROM sys.dm_exec_cached_plans AS cp 
CROSS APPLY sys.dm_exec_query_plan(plan_handle) AS qp 
CROSS APPLY query_plan.nodes('/ShowPlanXML/BatchSequence/Batch/Statements/StmtSimple') AS batch(stmt) 
CROSS APPLY stmt.nodes('.//Convert[@Implicit="1"]') AS n(t) 
JOIN INFORMATION_SCHEMA.COLUMNS AS ic 
  ON QUOTENAME(ic.TABLE_SCHEMA) = t.value('(ScalarOperator/Identifier/ColumnReference/@Schema)[1]', 'varchar(128)') 
  AND QUOTENAME(ic.TABLE_NAME) = t.value('(ScalarOperator/Identifier/ColumnReference/@Table)[1]', 'varchar(128)') 
  AND ic.COLUMN_NAME = t.value('(ScalarOperator/Identifier/ColumnReference/@Column)[1]', 'varchar(128)') 
WHERE t.exist('ScalarOperator/Identifier/ColumnReference[@Database=sql:variable("@dbname")][@Schema!="[sys]"]') = 1

2:非SARG謂詞會導致執行計劃從索引查找(Index Seek)變為索引掃描(Index Scan)

    SARG(Searchable Arguments)又叫查詢參數, 它的定義:用于限制搜索的一個操作,因為它通常是指一個特定的匹配,一個值的范圍內的匹配或者兩個以上條件的AND連接。不滿足SARG形式的語句最典型的情況就是包括非操作符的語句,如:NOT、!=、>;、!;、!>;NOT EXISTS、NOT IN、NOT LIKE等,另外還有像在謂詞使用函數、謂詞進行運算等。

2.1:索引字段使用函數會導致索引掃描(Index Scan)

SELECT nationalidnumber,
    loginid
FROM  humanresources.employee
WHERE SUBSTRING(nationalidnumber,1,3) = '112'


2.2索引字段進行運算會導致索引掃描(Index Scan)

    對索引字段字段進行運算會導致執行計劃從索引查找(Index Seek)變成索引掃描(Index Scan):

SELECT * FROM Person.Person WHERE BusinessEntityID + 10  260


一般要盡量避免這種情況出現,如果可以的話,盡量對SQL進行邏輯轉換(如下所示)。雖然這個例子看起來很簡單,但是在實際中,還是見過許多這樣的案例,就像很多人知道抽煙有害健康,但是就是戒不掉!很多人可能了解這個,但是在實際操作中還是一直會犯這個錯誤。道理就是如此!

SELECT * FROM Person.Person WHERE BusinessEntityID  250


2.3 LIKE模糊查詢回導致索引掃描(Index Scan)

    Like語句是否屬于SARG取決于所使用的通配符的類型, LIKE 'Condition%' 就屬于SARG、LIKE '%Condition'就屬于非SARG謂詞操作

SELECT * FROM Person.Person WHERE LastName LIKE 'Ma%'

SELECT * FROM Person.Person WHERE LastName LIKE '%Ma%'


3:SQL查詢返回數據頁(Pages)達到了臨界點(Tipping Point)會導致索引掃描(Index Scan)或表掃描(Table Scan)

What is the tipping point?
It's the point where the number of rows returned is "no longer selective enough". SQL Server chooses NOT to use the nonclustered index to look up the corresponding data rows and instead performs a table scan.

    關于臨界點(Tipping Point),我們下面先不糾結概念了,先從一個鮮活的例子開始吧:

SET NOCOUNT ON;
DROP TABLE TEST
CREATE TABLE TEST (OBJECT_ID INT, NAME VARCHAR(8));
CREATE INDEX PK_TEST ON TEST(OBJECT_ID)
DECLARE @Index INT =1;
WHILE @Index = 10000
BEGIN
  INSERT INTO TEST
  SELECT @Index, 'kerry';
  SET @Index = @Index +1;
END
UPDATE STATISTICS TEST WITH FULLSCAN;
SELECT * FROM TEST WHERE OBJECT_ID= 1

如上所示,當我們查詢OBJECT_ID=1的數據時,優化器使用索引查找(Index Seek)

上面OBJECT_ID=1的數據只有一條,如果OBJECT_ID=1的數據達到全表總數據量的20%會怎么樣? 我們可以手工更新2001條數據。此時SQL的執行計劃變成全表掃描(Table Scan)了。

UPDATE TEST SET OBJECT_ID =1 WHERE OBJECT_ID=2000;
UPDATE STATISTICS TEST WITH FULLSCAN;
SELECT * FROM TEST WHERE OBJECT_ID= 1

臨界點決定了SQL Server是使用書簽查找還是全表/索引掃描。這也意味著臨界點只與非覆蓋、非聚集索引有關(重點)。

Why is the tipping point interesting?
It shows that narrow (non-covering) nonclustered indexes have fewer uses than often expected (just because a query has a column in the WHERE clause doesn't mean that SQL Server's going to use that index)
It happens at a point that's typically MUCH earlier than expected… and, in fact, sometimes this is a VERY bad thing!
Only nonclustered indexes that do not cover a query have a tipping point. Covering indexes don't have this same issue (which further proves why they're so important for performance tuning)
You might find larger tables/queries performing table scans when in fact, it might be better to use a nonclustered index. How do you know, how do you test, how do you hint and/or force… and, is that a good thing?

4:統計信息缺失或不正確會導致索引掃描(Index Scan)

     統計信息缺失或不正確,很容易導致索引查找(Index Seek)變成索引掃描(Index Scan)。 這個倒是很容易理解,但是構造這樣的案例比較難,一時沒有想到,在此略過。

5:謂詞不是聯合索引的第一列會導致索引掃描(Index Scan)

SELECT * INTO Sales.SalesOrderDetail_Tmp FROM Sales.SalesOrderDetail;
CREATE INDEX PK_SalesOrderDetail_Tmp ON Sales.SalesOrderDetail_Tmp(SalesOrderID, SalesOrderDetailID);
UPDATE STATISTICS  Sales.SalesOrderDetail_Tmp WITH FULLSCAN;

下面這個SQL語句得到的結果是一致的,但是第二個SQL語句由于謂詞不是聯合索引第一列,導致索引掃描

SELECT * FROM Sales.SalesOrderDetail_Tmp
WHERE SalesOrderID=43659 AND SalesOrderDetailID10

SELECT * FROM Sales.SalesOrderDetail_Tmp WHERE SalesOrderDetailID10


您可能感興趣的文章:
  • mssql 建立索引
  • SQL2000 全文索引完全圖解
  • MSSQL 大量數據時,建立索引或添加字段后保存更改提示超時的解決方法
  • 關于重新組織和重新生成索引sp_RefreshIndex的介紹
  • SQL2005CLR函數擴展 - 關于山寨索引
  • MSSQL自動重建出現碎片的索引的方法分享
  • 理解Sql Server中的聚集索引
  • Sql Server中的非聚集索引詳細介
  • 詳解sqlserver查詢表索引
  • SQL2005重新生成索引的的存儲過程 sp_rebuild_index

標簽:通遼 阿里 南京 福建 廣安 陜西 馬鞍山 河北

巨人網絡通訊聲明:本文標題《在SQL SERVER中導致索引查找變成索引掃描的問題分析》,本文關鍵詞  在,SQL,SERVER,中,導致,索引,;如發現本文內容存在版權問題,煩請提供相關信息告之我們,我們將及時溝通與處理。本站內容系統采集于網絡,涉及言論、版權與本站無關。
  • 相關文章
  • 下面列出與本文章《在SQL SERVER中導致索引查找變成索引掃描的問題分析》相關的同類信息!
  • 本頁收集關于在SQL SERVER中導致索引查找變成索引掃描的問題分析的相關信息資訊供網民參考!
  • 推薦文章
    校园春色亚洲色图_亚洲视频分类_中文字幕精品一区二区精品_麻豆一区区三区四区产品精品蜜桃
    6080午夜不卡| 99re这里只有精品首页| 久久综合色鬼综合色| 一本大道久久a久久综合| 日本网站在线观看一区二区三区| 国产精品欧美一区喷水| 91麻豆精品久久久久蜜臀| 91美女片黄在线| 国产高清在线精品| 亚洲高清免费在线| 中文字幕一区二区三区av| 亚洲精品一区在线观看| 欧美日韩一区二区在线观看视频| 99re亚洲国产精品| 成人97人人超碰人人99| 国产美女在线精品| 极品少妇xxxx精品少妇| 日本aⅴ亚洲精品中文乱码| 午夜久久久久久久久久一区二区| 日韩毛片视频在线看| 国产精品网站在线| 亚洲国产岛国毛片在线| 国产精品美女久久久久久| 中文子幕无线码一区tr| 国产亚洲一区二区三区在线观看| 精品国产91久久久久久久妲己 | 麻豆一区二区在线| 日韩av在线播放中文字幕| 青草国产精品久久久久久| 久久不见久久见免费视频7| 国产麻豆精品久久一二三| 国产美女精品人人做人人爽| 国产风韵犹存在线视精品| 成人午夜碰碰视频| av不卡免费电影| 日本精品免费观看高清观看| 欧美在线制服丝袜| 欧美大肚乱孕交hd孕妇| 久久成人羞羞网站| 97精品国产97久久久久久久久久久久 | 中文字幕中文字幕一区| 亚洲免费观看视频| 日韩av在线发布| 成人精品电影在线观看| 欧美无乱码久久久免费午夜一区 | 麻豆一区二区在线| 成人黄动漫网站免费app| 91 com成人网| 国产嫩草影院久久久久| 亚洲自拍都市欧美小说| 午夜免费欧美电影| 国产一区二区看久久| 波多野结衣在线一区| 欧美日韩高清影院| 国产丝袜欧美中文另类| 亚洲一区影音先锋| 老司机精品视频一区二区三区| 亚洲欧洲制服丝袜| 国产一区二区三区电影在线观看 | wwww国产精品欧美| 久久久蜜臀国产一区二区| 久久久久久久久99精品| 天天综合色天天综合| 成人高清视频在线观看| 精品国产伦一区二区三区观看方式 | 国产成人精品一区二区三区网站观看| 色综合中文字幕| 久久久.com| 精品影院一区二区久久久| 在线观看不卡一区| 日韩美女视频19| 成人午夜精品在线| 制服丝袜亚洲精品中文字幕| 亚洲欧美日韩在线播放| 成人精品视频一区| 欧美肥妇bbw| 中文字幕一区二区视频| 免费人成网站在线观看欧美高清| 在线精品视频免费观看| 一区二区三区日韩精品| 色婷婷av一区二区三区之一色屋| 国内精品久久久久影院一蜜桃| 欧美日韩成人高清| 亚洲第一成人在线| 91免费看视频| 夜夜嗨av一区二区三区四季av| 国产米奇在线777精品观看| 久久影视一区二区| 久99久精品视频免费观看| 欧洲av在线精品| 依依成人综合视频| 欧美视频在线播放| 午夜亚洲国产au精品一区二区| 在线观看视频一区二区欧美日韩| 亚洲国产中文字幕| 欧美精品乱人伦久久久久久| 另类小说综合欧美亚洲| 精品国产91乱码一区二区三区| 激情久久久久久久久久久久久久久久| 欧美一区二区女人| 国产成人精品三级麻豆| 亚洲蜜臀av乱码久久精品蜜桃| av亚洲精华国产精华| 一区二区三区精密机械公司| 欧美一区二区三区在线视频| 狠狠色狠狠色合久久伊人| 国产精品看片你懂得| 欧美三级日韩在线| 麻豆精品久久精品色综合| 日韩写真欧美这视频| 成人18精品视频| 麻豆一区二区三区| 国产精品视频看| 日韩你懂的电影在线观看| 国产精品主播直播| 亚洲国产欧美一区二区三区丁香婷| 国产欧美精品一区二区三区四区| 国产精品一区二区91| 亚洲欧美色图小说| 欧美精品xxxxbbbb| 久久精品国产亚洲高清剧情介绍 | 99久久综合狠狠综合久久| 免费人成黄页网站在线一区二区 | 日韩高清在线不卡| 国产精品第一页第二页第三页| 91麻豆精品国产91久久久 | 欧美亚洲高清一区二区三区不卡| 国产99精品国产| 精品中文字幕一区二区| 亚洲一区二区综合| 欧美高清在线视频| 日本一区二区三区久久久久久久久不 | 国产一区二区日韩精品| 日韩高清国产一区在线| 亚洲成人精品一区二区| 一区2区3区在线看| 亚洲男女一区二区三区| 亚洲韩国精品一区| 五月天激情小说综合| 日韩影院在线观看| 丝袜亚洲另类欧美| 麻豆传媒一区二区三区| 极品尤物av久久免费看| 免费成人在线观看| 国内精品自线一区二区三区视频| 国产麻豆精品视频| 日本美女视频一区二区| 国产一区二区影院| 99久久综合国产精品| 色诱亚洲精品久久久久久| 欧美日韩一级视频| 精品国产麻豆免费人成网站| 久久久精品免费网站| 亚洲婷婷在线视频| 日本强好片久久久久久aaa| 日本欧美一区二区三区乱码| 国产高清在线观看免费不卡| 91久久香蕉国产日韩欧美9色| 欧美一区二区三区免费在线看| 在线不卡一区二区| 国产亚洲综合色| 午夜国产精品一区| 国产在线观看免费一区| 91福利国产成人精品照片| 精品国产一区二区三区久久影院| 国产亚洲福利社区一区| 亚洲精品欧美在线| 国产九九视频一区二区三区| 一本色道**综合亚洲精品蜜桃冫 | 色综合天天综合网国产成人综合天 | 亚洲一区二区av电影| 成人做爰69片免费看网站| 成人欧美一区二区三区小说| 日韩二区在线观看| 制服丝袜亚洲精品中文字幕| 亚洲激情图片一区| 色婷婷久久综合| 一区二区免费在线播放| 欧美在线免费播放| 美女尤物国产一区| 在线不卡一区二区| 青草av.久久免费一区| 欧美色网一区二区| 日韩av一级片| 精品乱码亚洲一区二区不卡| 免费观看日韩电影| 最新中文字幕一区二区三区| 在线综合+亚洲+欧美中文字幕| 丁香亚洲综合激情啪啪综合| 五月婷婷久久丁香| 国产喷白浆一区二区三区| 欧美日韩亚洲综合在线| 国产91综合网| 日本不卡中文字幕| 亚洲老司机在线| 久久久久久久久久久电影| 欧美日韩久久一区二区| 成人黄色免费短视频| 另类小说一区二区三区| 欧美一三区三区四区免费在线看|