索引查找

索引查找

 

问题引入:

 

表姐蓝发现用相同的列索引次序不同索引,然后同样的SQL语句执行时间却不同

 

CREATE INDEX INDEX_YN_CREATEDATE ON ORDERS(YN,CREATEDATE)

--118 毫秒

CREATE INDEX INDEX_YN_CREATEDATE ON ORDERS(CREATEDATE,YN)

--187 毫秒

 

 

 

分析过程:

 

 

 

------------------------------------------------------------------------

 

-- Author:  happyflystone 

 

-- Date  :  2009-02-13 15:00:07

-- Ver:     Microsoft SQL Server 2005 - 9.00.2047.00 (Intel X86)

--      Apr 14 2006 01:12:25

--      Copyright (c) 1988-2005 Microsoft Corporation

--      Standard Edition on Windows NT 5.0 (Build 2195: Service Pack 4)

--     

------------------------------------------------------------------------

 

-- Test Data: TA

IF OBJECT_ID('TA') IS NOT NULL

    DROP TABLE TA

Go

CREATE TABLE TA(PID INT PRIMARY KEY,ID INT,COL DATETIME)

Go

CREATE INDEX INDEX_YN_CREATEDATE2 ON TA(COL,ID)

GO

CREATE INDEX INDEX_YN_CREATEDATE1 ON TA(ID,COL)

GO

 

 

SELECT *

FROM TA WHERE COL >= CONVERT(VARCHAR(10),GETDATE()-300,120)

 AND COL <= CONVERT(VARCHAR(10),GETDATE(),120) AND ID = 1

 

|--INDEX SEEK(OBJECT:([CSDNDB].[DBO].[TA].[INDEX_YN_CREATEDATE2]), SEEK:([CSDNDB].[DBO].[TA].[COL] >= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE()-CONVERT_IMPLICIT(DATETIME,[@1],0),120),0) AND [CSDNDB].[DBO].[TA].[COL] <= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE(),120),0)),  WHERE:(CONVERT(CHAR(1),[CSDNDB].[DBO].[TA].[ID],0)=[@2]) ORDERED FORWARD)  

INDEX SEEK  OBJECT:([CSDNDB].[DBO].[TA].[INDEX_YN_CREATEDATE2]), SEEK:([CSDNDB].[DBO].[TA].[COL] >= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE()-CONVERT_IMPLICIT(DATETIME,[@1],0),120),0) AND [CSDNDB].[DBO].[TA].[COL] <= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE(),120),0)),  WHERE:(CONVERT(CHAR(1),[CSDNDB].[DBO].[TA].[ID],0)=[@2]) ORDERED FORWARD    [CSDNDB].[DBO].[TA].[PID], [CSDNDB].[DBO].[TA].[COL], [CSDNDB].[DBO].[TA].[ID]

 

SELECT *

FROM TA

WHERE ID = 1

AND COL >= CONVERT(VARCHAR(10),GETDATE()-300,120)

AND COL <= CONVERT(VARCHAR(10),GETDATE(),120)

|--INDEX SEEK(OBJECT:([CSDNDB].[DBO].[TA].[INDEX_YN_CREATEDATE1]), SEEK:([CSDNDB].[DBO].[TA].[ID]=CONVERT_IMPLICIT(BIGINT,[@1],0) AND [CSDNDB].[DBO].[TA].[COL] >= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE()-CONVERT_IMPLICIT(DATETIME,[@2],0),120),0) AND [CSDNDB].[DBO].[TA].[COL] <= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE(),120),0)) ORDERED FORWARD)

INDEX SEEK OBJECT:([CSDNDB].[DBO].[TA].[INDEX_YN_CREATEDATE1]), SEEK:([CSDNDB].[DBO].[TA].[ID]=CONVERT_IMPLICIT(BIGINT,[@1],0) AND [CSDNDB].[DBO].[TA].[COL] >= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE()-CONVERT_IMPLICIT(DATETIME,[@2],0),120),0) AND [CSDNDB].[DBO].[TA].[COL] <= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE(),120),0))

 

 查询计划如下:

 

(CSDN不让上传图片)

 

 

 

――解释

 

索引查找

 

索引查找操作是SQL Server从索引中读取数据采用的迭代器,返回特定谓词上一个或多个范围内的数据行,仅扫描满足该谓词的数据页,查询开销显然要比表中总记录数的开销低,因此,对于大数据量的表进行查询时,使用查找谓词是比较有效率的。

 

 

谓词与谓词覆盖

 

         索引要确保包含或覆盖查询中引用的列集合,关于查询优化的例子很多,对列是否能进行索引查找相信大家不陌生吧。

 

 

好,对上面的例子进行简要说明,第一个查询使用INDEX_YN_CREATEDATE2(COL,ID)索引,在第一个键列上进行索引查找,然后使用residual谓词来估计ID

 

SEEK:([CSDNDB].[DBO].[TA].[COL] >= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE()-CONVERT_IMPLICIT(DATETIME,[@1],0),120),0) AND [CSDNDB].[DBO].[TA].[COL] <= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE(),120),0)),  WHERE:(CONVERT(CHAR(1),[CSDNDB].[DBO].[TA].[ID],0)=[@2])

 

 

第二个查询在IDCOL索引上进行利用索引INDEX_YN_CREATEDATE1(IDCOL)进行查找。

 

SEEK:([CSDNDB].[DBO].[TA].[ID]=CONVERT_IMPLICIT(BIGINT,[@1],0) AND [CSDNDB].[DBO].[TA].[COL] >= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE()-CONVERT_IMPLICIT(DATETIME,[@2],0),120),0) AND [CSDNDB].[DBO].[TA].[COL] <= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE(),120),0)) ORDERED FORWARD)

 

INDEX SEEK OBJECT:([CSDNDB].[DBO].[TA].[INDEX_YN_CREATEDATE1]), SEEK:([CSDNDB].[DBO].[TA].[ID]=CONVERT_IMPLICIT(BIGINT,[@1],0) AND [CSDNDB].[DBO].[TA].[COL] >= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE()-CONVERT_IMPLICIT(DATETIME,[@2],0),120),0) AND [CSDNDB].[DBO].[TA].[COL] <= CONVERT_IMPLICIT(DATETIME,CONVERT(VARCHAR(10),GETDATE(),120),0))

 

 

DROP TABLE TA

GO

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值