MS SQL: 查询 ID 降序的性能

MS SQL: Performance for querying ID descending

此问题与 Microsoft SQL 服务器中的 table 有关,通常使用 ORDER BY Id DESC 查询。

将主键设置为 PRIMARY KEY CLUSTERED (Id DESC) 是否会提高性能?或者是否需要索引?还是没有它时它变得尽可能快?

Table:

CREATE TABLE [dbo].[Items] (
    [Id] INT IDENTITY (1, 1) NOT NULL,
    [Category] INT NOT NULL,
    [Name] NVARCHAR(255) NULL,
    CONSTRAINT [PK_Items] PRIMARY KEY CLUSTERED ([Id] ASC)
)

查询:

SELECT TOP 1 * FROM [dbo].[Items]
WHERE Catgory = 123
ORDER BY [Id] DESC

Would there be a performance benefit from setting the primary key to PRIMARY KEY CLUSTERED (Id DESC)?

如您所见:视情况而定。

过滤器在类别 = 123 上。要查找类别 123 的所有条目,因为没有定义索引,服务器必须执行 table 扫描。除非你有一个非常大的结果集,和/或一些非常可笑的错误配置的 tempdb 和非常低的内存(因为只有当 运行 tempdb 内存不足时才使用磁盘)hte 结果的排序与table扫描。

你真的跟错了尾巴。您更有可能通过向 Cateogory 添加 non-unique 索引来加快查询速度,以便查询可以根据您的查询条件快速预过滤数据。

如果您要分析此查询的查询计划(您应该这样做——从技术上讲,如果您不付出一些努力,我们甚至不应该回答这个问题,并且查看查询计划就像您做的第一件事)您很可能会看到时间花在了查询上,而不是结果排序上。

按照以下没有区别

我建议在 (category, id desc) 上定义一个索引。 它将为您的查询提供最佳性能。

正如其他人所指出的,类别索引(假设您没有)是最大的性能提升。

但至于你的实际问题。对于像您这样的单个 order by 查询,就性能而言,query/index 是按 desc 还是 asc 排序并不重要。 SQL 服务器可以很容易地交换这些(从数据结构的开头或结尾开始)

性能成为性能问题的地方是:

  1. 超过 order by
  2. 您的索引有多于一列
  3. 您的 order by 与指数相反。

所以,假设您的主键有 ID asc 和类别 asc,然后您通过 ID asc 和类别 desc 进行查询。然后SQL 服务器无法使用索引上的顺序进行搜索。

有一些注意事项和陷阱。经过一番搜索,这个答案似乎列出了它们:

SQL Server indexes - ascending or descending, what difference does it make?

当只有一列时,按升序或降序创建索引在“ORDER BY”中没有太大区别,但是当需要对数据进行两个不同方向的排序时,一列升序和以降序排列的另一列索引的创建方式确实有很大的不同。

看这篇文章做的很多例子:

https://www.mssqltips.com/sqlservertip/1337/building-sql-server-indexes-in-ascending-vs-descending-order/

在您的场景中,我建议您在不包含“Id”的类别列上创建索引,因为聚簇索引始终包含在非聚簇索引中。