基础数据都相同
语句1:实际执行计划中的估计子树:4694
语句2:实际执行计划中的估计子树:2676.18
语句1应该比语句2运行更耗时的,但实际运行耗时,反而是语句1(10分钟)比语句2(12分钟)的更短些,这是如何理解?还望指点下,谢谢!
没法上传执行计划文件

解决方案 »

  1.   

    语句1:
    SELECT AutoID, phone, grade, m1.MsgID, m1.IsBind, m1.GIndex into #todo1
    FROM #user AS u
    cross apply 
    (
    SELECT top 1 MsgID, IsBind, GIndex  
    FROM #Msg AS m
    WHERE m.GradeGroup like '%,' + cast(u.grade as varchar(5)) + ',%' 
    and m.cityName like '%,' + cast(u.code as varchar(5)) + ',%' 
    and m.sex like '%,' + cast(u.sex as varchar(5)) + ',%' 
    and not exists(select 1 
    from #msg n 
    join #log l on l.phone = u.phone and l.MsgID = n.MsgID
    where m.ParentID = n.ParentID)
    order by m.IsBind, m.GIndex, m.GradeLevel, m.EnableDay, m.orderid, m.SexLen, m.cityflag, m.msgid desc
    ) as m1表 '#log'。扫描计数 1,逻辑读取 53328 次,物理读取 24794 次,预读 11390 次,lob 逻辑读取 0 次,lob 物理读取 0 次,lob 预读 0 次。
    表 '#Msg'。扫描计数 22363702,逻辑读取 49129678 次,物理读取 4 次,预读 0 次,lob 逻辑读取 0 次,lob 物理读取 0 次,lob 预读 0 次。
    表 '#user'。扫描计数 17,逻辑读取 1013 次,物理读取 0 次,预读 0 次,lob 逻辑读取 0 次,lob 物理读取 0 次,lob 预读 0 次。
    表 'Worktable'。扫描计数 36901862,逻辑读取 239293812 次,物理读取 0 次,预读 0 次,lob 逻辑读取 0 次,lob 物理读取 0 次,lob 预读 0 次。(157311 行受影响)
      

  2.   

    语句2:
    SELECT AutoID, phone, grade, m1.MsgID, m1.IsBind, m1.GIndex into #todo1
    FROM #user AS u
    cross apply 
    (
    SELECT top 1 MsgID, IsBind, GIndex  
    FROM #Msg AS m
    WHERE m.GradeGroup like '%,' + cast(u.grade as varchar(5)) + ',%' 
    and m.cityName like '%,' + cast(u.code as varchar(5)) + ',%' 
    and m.sex like '%,' + cast(u.sex as varchar(5)) + ',%' 
    and not exists(select 1 
    from #msg n 
    join #log l on l.phone = u.phone and l.MsgID like '%,' + cast(n.MsgID as varchar(7)) + ',%' 
    where m.ParentID = n.ParentID)
    order by m.IsBind, m.GIndex, m.GradeLevel, m.EnableDay, m.orderid, m.SexLen, m.cityflag, m.msgid desc
    ) as m1表 '#log'。扫描计数 39636434,逻辑读取 202694250 次,物理读取 0 次,预读 14 次,lob 逻辑读取 0 次,lob 物理读取 0 次,lob 预读 0 次。
    表 '#Msg'。扫描计数 22667508,逻辑读取 50160883 次,物理读取 0 次,预读 1 次,lob 逻辑读取 0 次,lob 物理读取 0 次,lob 预读 0 次。
    表 '#user'。扫描计数 17,逻辑读取 1013 次,物理读取 0 次,预读 0 次,lob 逻辑读取 0 次,lob 物理读取 0 次,lob 预读 0 次。
    表 'Worktable'。扫描计数 0,逻辑读取 0 次,物理读取 0 次,预读 0 次,lob 逻辑读取 0 次,lob 物理读取 0 次,lob 预读 0 次。(157311 行受影响)
      

  3.   

    上面两个语句,基本相同,不同之处理就是:
    语句1.and l.MsgID = n.MsgID
    语句2.and l.MsgID like '%,' + cast(n.MsgID as varchar(7)) + ',%'  
    有建立相应的索引,执行计划中也有使用到这些索引
      

  4.   

    在索引用LIKE%%或者CAST是不会走索引的。。
      

  5.   

    无法使用索引的Select语句 及时正确的创建了索引,在select的时候也要正确的使用。否则就是可能无法在查询过程中应用索引。1.对索引列应用了函数。就不会走索引了  select * from tb where abs(id)=20 2.对索引列使用了like ‘%1’select * from tb where id like '%1xxxx22' 就不会用到索引了通配符用到后面就可以使用到索引 了select * from tb where id like '1xxxx22%'3.where子句对列进行了类型转换 是无法使用到索引的select * from tb where  cast(name as varchar(20))='scott';4.组合索引的顺序很重要在组合查询中多个条件查询只有在组合索引的第一列索引查会使用 例如:有一个组合索引 [sql] view plaincopyprint?
    create index  id_name_fsex_index on test(name,sex,id)  
    select name from test where   name='mrzhou' and sex='男'  create index  id_name_fsex_index on test(name,sex,id)
    select name from test where   name='mrzhou' and sex='男'这样才会有索引的使用
    http://blog.csdn.net/szstephenzhou/article/details/7774558
      

  6.   

    看下 统计信息  exec sp_autostats 'tb'   。。
      

  7.   

    DBCC SHOW_STATISTICS(‘表名’,‘索引’)
      

  8.   

    在执行环境相同的情况下,通常是子树成本越小越快,但SQL Server在以下情况下估计子树成本可能会不准确:
    1、多CPU并行计算
    2、存在临时表或表变量楼主的语句中存在临时表,导致估计子树成本不准确,所以才会出现语句1比语句2更快。
      

  9.   

    第一个搜索引了,第二个like是不会走索引的。差别是第一个索引查找,第二个索引扫描。