【问题标题】:TSQL Partition by with Order byTSQL Partition by with Order by
【发布时间】:2013-10-11 03:04:11
【问题描述】:

我注意到当我使用如下分区时

SELECT
ROW_NUMBER() OVER(PARTITION BY categoryid
ORDER BY unitprice, productid) AS rownum,
categoryid, productid, productname, unitprice
FROM Production.Products;

结果集以正确的分区和顺序返回给我。

这是否意味着我不必在末尾提供 Order BY 子句来绝对保证我想要的顺序?

谢谢

【问题讨论】:

    标签: sql-server tsql sql-order-by partition


    【解决方案1】:

    没有。

    为保证结果顺序,您必须使用适用于最外层查询的ORDER BY。其他一切都只是巧合。

    SELECT
    ROW_NUMBER() OVER(PARTITION BY categoryid
    ORDER BY unitprice, productid) AS rownum,
    categoryid, productid, productname, unitprice
    FROM Production.Products
    ORDER BY categoryid,unitprice,productid;
    

    ORDER BY 有两个角色:

    • 实际定义另一个功能的工作方式。当使用TOP 时,或者在OVER() 分区函数中时,这是正确的。它并不要求进行排序,它只是说“这个定义只有在我们认为结果集中的行以特定顺序出现时才有意义——这就是我想要使用的”
    • 规定结果集的排序顺序。当它是作为特定查询一部分的最外层语句上的 ORDER BY 子句时是正确的 - 而不是在子查询、CTE、OVER() 分区函数等中。

    有时您会体验到它同时用于两种含义 - 当最外层的语句包含 TOPOFFSET/FETCH 时,它会同时用于两种用途。

    【讨论】:

    • +1 OVER() 子句中的ORDERBY 仅规定如何分配行号值,它不保证最终结果集的顺序
    • 我很难理解下面的内容,插入 Sales.MyOrders(orderid, custid, empid, orderdate) SELECT NEXT VALUE FOR Sales.SeqOrderIDs OVER(ORDER BY orderid), custid, empid, orderdate FROM Sales.Orders WHERE custid = 1;这本书说“带有 ORDER BY 列表的 OVER 子句来控制将序列值分配给结果行的顺序”如果我能得到澄清,那就太好了
    猜你喜欢
    • 1970-01-01
    • 2021-02-10
    • 1970-01-01
    • 1970-01-01
    • 2021-10-29
    • 1970-01-01
    • 1970-01-01
    • 2019-03-21
    • 2014-01-30
    相关资源
    最近更新 更多