SQL Server 2008:嵌套语句

4
我正在尝试编写一个计算发票总额的语句,每个发票都有多个产品和价格。我得到了以下代码:
SELECT SUM((UnitPrice-Discount)*Quantity)
FROM tblOrderDetails 
WHERE OrderID= OrderID 
GROUP BY OrderID ORDER BY OrderID 

这部分目前运行良好,现在我需要从另一个表格(tblOrder)中添加货运费用,但我卡住了,我尝试了:

SELECT OrderID, Freight+
    (SELECT SUM((UnitPrice-Discount)*Quantity)
    FROM tblOrderDetails 
    WHERE OrderID= OrderID 
    GROUP BY OrderID 
    ORDER BY OrderID)
FROM tblOrders

但是我一直得到错误提示:

在视图、内联函数、派生表、子查询和公共表达式中,ORDER BY 子句无效,除非同时指定 TOP 或 FOR XML。

如有帮助,将不胜感激。

4
它的意思就是字面上的意思 :-) 通常只有在 SQL 中保证最终结果集的顺序。在这种情况下,ORDER BY 没有任何影响。 - user166390
4个回答

2

这句话的意思就是它所说的那样 :-)

当使用ORDER BY时,只有最终结果集(返回给客户端的结果集)的排序是有保证的。所有中间结果集都只是记录的集合,其中项目的顺序可能会变化。ORDER BYTOP一起工作是因为它基于ORDER BY建立的“视图”限制了结果集 - 但是,除非这是顶层ORDER BY,否则它不保证最终结果集的顺序(只是选择了“正确”的TOP记录)。

也就是说,

SELECT FOO FROM (
  SELECT TOP 10 FOO FROM X
  ORDER BY FOO ASC) BAR

最终结果集中的记录没有保证顺序; FOO值可以以任何顺序出现。

祝编码愉快。


2

尝试:

SELECT o.OrderID, o.Freight + SUM((d.UnitPrice-d.Discount)*d.Quantity)
FROM tblOrderDetails d
JOIN tblOrders o ON o.OrderId = d.OrderId
GROUP BY o.OrderID, o.Freight
ORDER BY o.OrderID, o.Freight -- Freight avoids a potential re-order

1

移除 ORDER BY OrderID

SELECT OrderID, Freight+
    (SELECT SUM((UnitPrice-Discount)*Quantity)
    FROM tblOrderDetails 
    WHERE OrderID= OrderID 
    GROUP BY OrderID)
FROM tblOrders

如错误信息所述,子查询中是不允许使用此语法的(没有 TOP 或 FOR XML),而且对于您的需求也没有什么实际效用。


1

你不能在子查询中使用ORDER BY。我猜你在开发查询的那部分时忘记把它去掉了。把它去掉就没问题了。

SELECT OrderID, Freight+
    (SELECT SUM((UnitPrice-Discount)*Quantity)
    FROM tblOrderDetails 
    WHERE OrderID= OrderID 
    GROUP BY OrderID)
FROM tblOrders

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接