Sql server 在SQL Server SELECT查询中替换索引搜索上的索引扫描

Sql server 在SQL Server SELECT查询中替换索引搜索上的索引扫描,sql-server,sql-server-2014,Sql Server,Sql Server 2014,第一个查询可以很好地用于索引查找: 你应该试试: SELECT * FROM dbo.MessageLast c JOIN #t t on c.partner_id = t.partner_id where c.Stat_Date >= '2017-04-25' and c.Stat_Date <= '2017-04- 26' 你应该试试: SELECT * FROM dbo.MessageLast c JOIN

第一个查询可以很好地用于索引查找:

你应该试试:

SELECT *
FROM dbo.MessageLast c
        JOIN #t t on c.partner_id = t.partner_id
where  c.Stat_Date >= '2017-04-25' 
                and c.Stat_Date <= '2017-04- 26' 
你应该试试:

SELECT *
FROM dbo.MessageLast c
        JOIN #t t on c.partner_id = t.partner_id
where  c.Stat_Date >= '2017-04-25' 
                and c.Stat_Date <= '2017-04- 26' 

这是因为索引并没有覆盖:您正在选择表中的所有字段

当索引不包含查询时,sql server应执行两个步骤:

1索引寻找匹配谓词的PK值和包含的列SD

2键查找在聚集索引中查找每一行,以查找索引中未包含的列的值

因此,在某些情况下,查询优化器决定全表扫描比这两个步骤快


您可以用SELECT dt make index covering替换SELECT*并接收索引搜索。这里有更多信息:

发生这种情况是因为索引没有覆盖:您正在选择表中的所有字段

当索引不包含查询时,sql server应执行两个步骤:

1索引寻找匹配谓词的PK值和包含的列SD

2键查找在聚集索引中查找每一行,以查找索引中未包含的列的值

因此,在某些情况下,查询优化器决定全表扫描比这两个步骤快


您可以用SELECT dt make index covering替换SELECT*并接收索引搜索。这里有更多信息:

您的临时表没有索引,因此只有完整的表扫描可以工作。除此之外,表变量的执行速度并不比表快。事实上,如果用作TVP,它们的速度会慢得多。编译查询时,TVP为空,因此没有统计信息。临时表没有索引,因此只能进行完整表扫描。除此之外,表变量的执行速度并不比表快。事实上,如果用作TVP,它们的速度会慢得多。编译查询时,TVP为空,因此没有统计信息
 SELECT *
 FROM   dbo.MessageLast c with (forceseek)

 WHERE  c.Stat_Date >= '2017-04-25'
        and c.Stat_Date <= '2017-04-26'
        and exists(select
                       * 
                   from  #d as d where  c.partner_id = d.partner_id)
create table _tBig (
  dt Date
, id1 Int
, id2 Int
, id3 Int
, id4 Int
, txt Varchar(500)
) 
create clustered index PK_tBig  on _tBig (id4,dt)



--truncate table _tBig

declare @i Int = 1
set nocount on
while @i < 10000
begin
    insert  into _tBig with (tablock)
            (dt
           , id1
           , id2
           , id3
           , id4
           , txt
            )
    select top (1000)
            DateAdd(day, Rand() * 365 + 1, GetDate())
          , Row_Number() over (order by O.[object_id])
          , Rand() * 10000000 + 1
          , Rand() * 10000000 + 1
          , Rand() * 10000000 + 1
          , NewId()
    from    sys.all_objects O

    set @i += 1

end 


create table _tId (id1 Int)



--truncate table _tId

insert  into _tId
        (id1
        )
select top (5)
        Row_Number() over (order by O.[object_id])
from    sys.all_objects O



select  *
from    _tBig as tb
where   tb.dt >= '20170517'
        and tb.dt < '20170519'
        and tb.id1 in (1, 2, 3, 4, 5)

create index IX_Big on _tBig (dt,id1)

select  *
from    _tBig as tb
inner join _tId as ti on ti.id1 = tb.id1
where   tb.dt >= '20170517'
        and tb.dt < '20170519'


create index IX_Big2 on _tBig (id1,dt)

select  *
from    _tBig as tb
inner join _tId as ti on ti.id1 = tb.id1
where   tb.dt >= '20170517'
        and tb.dt < '20170519'

--drop table dbo._tBig
--drop table dbo._tId
SELECT *
FROM dbo.MessageLast c
        JOIN #t t on c.partner_id = t.partner_id
where  c.Stat_Date >= '2017-04-25' 
                and c.Stat_Date <= '2017-04- 26'