SQL Server 聚集索引是否取代了 RID 查找“索引”?

发布于 2024-09-19 10:58:51 字数 290 浏览 1 评论 0原文

当 SQL Server 中的表具有聚集索引时,是否意味着所有索引查询都将通过聚集索引进行?

例如,如果我有一个带有单个非聚集索引(索引一列)的表并通过该列搜索行,它将执行 Index Seek -> RID->数据行查找->结果

但是,如果我在不同的列上添加聚集索引,那么相同的查询将执行以下Index Seek ->提取聚类键->聚集索引查找->结果

这对我来说意味着非聚集索引不再以叶子处的 RID“终止”,而是以聚集索引的聚集键“终止”?是这样吗?

When a table has a clustered index in SQL Server does that mean that all indexed queries will go via the clustered index?

For example if I have a table with a single non-clustered index (indexing one column) and search for a row via that column it will do Index Seek -> RID -> Data row lookup -> Result

But if I add a clustered index on a different column then the same query will do the following Index Seek -> Extract clustering key -> Clustered index seek -> Results

This implies to me that the non-clustered index no longer 'terminates' with a RID at the leaf but with a clustering key of the clustered index? Is that right?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

杀お生予夺 2024-09-26 10:58:51

是的,你已经很清楚了。

当您有聚集索引时,任何非聚集索引也将包括聚集索引中的列,作为它们对实际数据的“查找”。

如果您在非聚集索引中搜索值,并且需要访问基础数据的其余列,则 SQL Server 会从该非聚集索引到索引执行“书签查找”(或“键查找”)。聚集索引(在叶级节点中包含数据本身)。使用聚集索引,您不再需要 RID - 因此,如果 RID 更改(当数据从一个页面移动到另一页面时),您不必更新所有索引页。

书签查找是相当昂贵的操作,因此您可以通过 INCLUDE 语句向非聚集索引添加其他列。这样,您的非聚集索引将在其叶级页面上包含这些附加列,并且如果您只需要该数据集中包含的列,则可以从非聚集索引本身满足您的查询(即在这种情况下,它称为“覆盖索引”),您可以为自己节省一系列书签查找。

Yes, you got it pretty much figured out.

When you have a clustered index, then any non-clustered index will also include the column(s) from the clustered index as their "lookup" into the actual data.

If you search for a value in a non-clustered index, and you need to access the remaining columns of the underlying data, then SQL Server does a "bookmark lookup" (or "key lookup") from that non-clustered index into the clustered index (which contains the data itself, in the leaf-level nodes). With a clustered index, you don't need the RID's anymore - and thus you don't have to update all your index pages if a RID changes (when data gets moved from one page to another).

Bookmark lookups are rather expensive operations, so you can add additional columns to your non-clustered indices via the INCLUDE statement. With this, your non-clustered index will contain those additional columns on its leaf-level pages, and if you only need columns that are contained in that set of data, your query can be satisfied from the non-clustered index itself (in that case, it's called a "covering index") and you can save yourself a series of bookmark lookups.

路还长,别太狂 2024-09-26 10:58:51

不是。并非每个查询都会使用聚集索引。如果查询被非聚集索引“覆盖”(查询所需的所有列都包含在 NC 索引中),那么 SQL Server 将只需要读取这些索引页,而不执行书签查找。事实上,只要有可能,优化器通常更愿意使用覆盖 NC 索引,因为 NC 索引通常小于聚集索引,因此扫描速度通常更快。

No. Not every query will use the clustered index. If a query is "covered" by a nonclustered index (all the columns required for the query are contained in the NC index) then SQL Server will only need to read those index pages and not perform the bookmark lookup. In fact the optimizer will often prefer to use a covering NC index whenever it can because the NC index is usually smaller than the clustered index and is therefore usually faster to scan.

失退 2024-09-26 10:58:51

当 SQL Server 中的表具有聚集索引时,是否意味着所有索引查询都将通过聚集索引进行?

否。

如果查询仅使用二级索引和/或聚集索引覆盖的字段,则可能(并且很可能)会首选二级索引。

CREATE TABLE test (id INT NOT NULL PRIMARY KEY, value1 INT NOT NULL, value2 INT NOT NULL)

CREATE INDEX ix_test_value2 ON test (value2)

SELECT  value2, id
FROM    test

上面的查询很可能会使用 ix_test_value2,因为它包含查询所需的所有信息,但大小较小。

这对我来说意味着非聚集索引不再以叶子处的 RID 而是以聚集索引的聚集键“终止”?是这样吗?

是的,有一些小的修正:

  • 如果聚集索引不是唯一的,则辅助索引中的行指针由聚集键加上一个名为 uniquiefier 的特殊隐藏列(实际上,该列也附加到聚集索引)。

  • ,则仅将聚集键的缺失部分附加为行指针。
  • 如果二级索引声明为UNIQUE,则聚集键仅附加到二级索引的叶级记录。

When a table has a clustered index in SQL Server does that mean that all indexed queries will go via the clustered index?

No.

If a query only uses the fields covered by a secondary index and/or clustered index, the secondary index may (and most probably will) be preferred.

CREATE TABLE test (id INT NOT NULL PRIMARY KEY, value1 INT NOT NULL, value2 INT NOT NULL)

CREATE INDEX ix_test_value2 ON test (value2)

SELECT  value2, id
FROM    test

The query above will most probably use ix_test_value2, since it contains all the information the query needs, but is less in size.

This implies to me that the non-clustered index no longer 'terminates' with a RID at the leaf but with a clustering key of the clustered index? Is that right?

Yes, with some little corrections:

  • If the clustered index is non-unique, the row pointer in the secondary index consists of the clustered key plus a special hidden column called uniquiefier (actually, this column is appended to the clustered index too).

  • If the secondary index covers some of the columns of the clustered index,, only the missing parts of the clustered key are appended as row pointers.

  • If the secondary index is declared UNIQUE, clustered key is appended only to the leaf-level records of the secondary index.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文