为什么 Top , OFFset fetch , Rownumber 查询仅仅通过改变升序和降序就得到不同的结果?

Why Top ,OFFset fetch , Rownumber query gives different outcome just by changing the ascending and descending order?

使用 AdventureWorks2012 数据库

第 1 步:执行以下查询:

select *
from 
    (select
         ROW_NUMBER() OVER(order by listprice desc) AS RowNumber,*
     from Production.Product) as a
where 
    a.RowNumber between 1 and 2

select *
from Production.Product
order by ListPrice desc
offset 0 rows fetch next 2 rows only

select top 2 Productid, ListPrice
from Production.Product
order by ListPrice desc

第 2 步:现在执行以下查询:

select *
from 
    (select
         ROW_NUMBER() OVER(order by listprice asc) AS RowNumber,*
     from Production.Product) as a
where 
     a.RowNumber between 1 and 2

select *
from Production.Product
order by ListPrice asc
offset 0 rows fetch next 2 rows only

select top 2 Productid, ListPrice 
from Production.Product 
order by ListPrice asc

查看两种情况下的产品 ID(DESC 和 ASC)

这一点也不奇怪。您了解到,多行具有相同的 listprice 值。当 listprice 有联系时,对于具有相同值的键,排序是 不确定

换句话说,SQL 服务器(和一般数据库)中的排序不稳定。 运行 多次相同的查询可以 return 不同的排序。同样,对查询的微小更改可能会导致不同的排序——对于具有相同值的键。

这个其实很好理解。 SQL 个表表示 个无序 个集合。因此,它们没有 natural 顺序。数据库无法对具有相同键值的行进行规范排序。

要解决此问题,只需在订单中添加一个唯一 ID,例如:

order by listprice desc, productid

添加额外的唯一键使排序稳定。