zoukankan      html  css  js  c++  java
  • 《SQL Server 2005技术内幕:TSQL查询》上的一处错误

    SQL Server 2005技术内幕:T-SQL查询》一书的第7章,“使用TOPApply解决常见问题”一节中,介绍了多种方式获得每个销售员的最新订单。

    其中第三种方式是这样的。书上只是说这是个“糟糕计划”,其实是糟糕T-SQL代码造成的。而这个方案其实可以优化成为作者给出的三个用于SQL Server 2000的方案中最好的一个。

    SELECT OrderID, CustomerID, E.EmployeeID, OrderDate, RequiredDate
    FROM dbo.Employees AS E
       
    JOIN dbo.Orders AS O1
         
    ON OrderID IN
           (
    SELECT TOP(3) OrderID
            
    FROM dbo.Orders AS O2
            
    WHERE O2.EmployeeID = E.EmployeeID
            
    ORDER BY OrderDate DESC, OrderID DESC);

    有看出问题吗?再看看它上面的图。


    注意第二个
    Nested Loops上有一个感叹号。知道是什么原因了吗?如果还没有看出问题的话,可以参考书上271页,讲述联接的部分。 

    这个警告是“没有联接谓词”,说明白些,就是指上面的SQL代码中的JOIN没有相关的ON子句。注意不是说没有ON子句,是说没有与JOIN相关的ON子句。 

    没有ON子句的JOIN就变成了CROSS JOIN。能不慢吗? 

    大家有兴趣可以自己想一想如何优化这个SQL。我在AdventureWorks上做的测试,运行速度提高近100倍。 

    答案如下: 

    SELECT OrderID, CustomerID, E.EmployeeID, OrderDate, RequiredDate
    FROM dbo.Employees AS E
       
    JOIN dbo.Orders AS O1
         
    ON O1.EmployeeID = E.EmployeeID AND OrderID IN
           (
    SELECT TOP(3) OrderID
            
    FROM dbo.Orders AS O2
            
    WHERE O2.EmployeeID = E.EmployeeID
            
    ORDER BY OrderDate DESC, OrderID DESC);

    其执行计划如下图所示:


    书中有错误是很正常的。读一本书,其实可以把找出错误的个数,作为衡量书是不是真正读懂的一个标准。我自己读书就有一个习惯,把书的第一个空白页当勘误表。一般发现翻译错误、字词遗漏什么的也不值当发上来,不过这个错误感觉就比较严重了。

  • 相关阅读:
    圣诞节快乐 | 圣诞特效来了!!
    前端特效demo | 值得收藏的6个 HTML5 Canvas 实用案例
    前端特效demo | 一起围观 10 种创意时钟
    即学即用,轻松搞定这些选择器!(下)
    架构师究竟要不要写代码?
    偷懒秘诀之变量篇
    弹幕,是怎样练成的?
    [C++]模板类和模板函数
    [C++]typedef用法
    [面试]CVTE 2019提前批 Windows应用开发一面
  • 原文地址:https://www.cnblogs.com/nankezhishi/p/insidetsqlqueryerror.html
Copyright © 2011-2022 走看看