【问题标题】:Index advise SQL Server 500M records索引建议 SQL Server 500M 记录
【发布时间】:2019-03-12 11:52:05
【问题描述】:

我有一个结构如下的表:

primary+foreignkey1
primary+foreignkey2
primary+foreignkey3
primary+foreignkey4
primary+foreignkey5
primary+foreignkey6
string
int
varbinary

它非常像一个事实表,其中外键引用维度。尺寸非常小,每个大约 2000 行。然而,主事实表有 5 亿行。

目前,性能非常非常糟糕。简单的查询需要很长时间。数据每 2 年更改一次,因此非常静态。

我们目前只有所有 pk 值的聚集索引:

CREATE TABLE table(
    [id1] [int] NOT NULL,
    [id2] [int] NOT NULL,
    [id2] [int] NOT NULL,
    [id4] [int] NOT NULL,
    [id5] [int] NOT NULL,
    [id6] [int] NOT NULL,
    [location] [varchar](50) NOT NULL,
    [year] smallint NOT NULL,
    [text] [decimal](10, 4) NULL,
    [hash] [varbinary](50) NOT NULL,
 CONSTRAINT [pk_1] PRIMARY KEY CLUSTERED 
(
    id1 ASC,
    id2 ASC,
    id3 ASC,
    id4 ASC,
    id5 ASC,
    id6 ASC,
    location ASC,
    year asc

)

任何人都可以建议我在最佳实践索引中查询表时优化性能吗?

【问题讨论】:

  • 索引用于优化查询。您需要对表格的使用方式有所了解。
  • 什么版本的 SQL Server ?对于 2014+(最好是 2016+),对于这种事实表,如果您没有明确的查询模式,您可以使用非聚集列存储索引(这就是它们存在的原因)
  • 对 Bogdan 的评论加一,但是我会使用聚集列存储索引
  • 我们使用的是 sql server 2016,所以我们可以使用任何一个。哪个最好?聚集或非聚集列存储索引?
  • @ImperialBert,(恕我直言)集群,它被构建为对星型模式工作负载非常有效。此外,它会使事实表缩小 5-20 倍。缺点 - 外键限制.. 它们是可能的,但需要额外的 btree 索引

标签: sql sql-server indexing database-administration


【解决方案1】:

(免责声明:本文基于个人观点)

首先,您的集群主键看起来有点无意义:

CONSTRAINT [pk_1] PRIMARY KEY CLUSTERED 
(
    id1 ASC,
    id2 ASC,
    id3 ASC,
    id4 ASC,
    id5 ASC,
    id6 ASC,
    location ASC,
    year asc
)
  • 它几乎不保证任何唯一性,因为几乎所有的列都放在那里,
  • 它会减慢插入速度
  • 它使所有其他非聚集索引也毫无意义,因为它们将包含所有非聚集索引中聚集索引的所有列出的列。
  • 仅通过在列id1 上搜索值或多或少会有所帮助

其次,如果没有看到您的查询,很难得出任何结论,除非很明显,您有一个星型模式数据集市。 Microsoft 为此类分析工作负载引入了列存储索引。

为了强调上面所说,聚集列存储索引是默认在 Azure SQL 数据仓库表上创建的,因此在大型数据集上聚合时它真的很亮

因此,由于星型模式、行数和明显的分析工作量,只是一般建议:

  • 考虑在事实表上尝试聚集列存储索引。它将是一个单一的索引,但它涵盖了所有列
  • 考虑在 ETL 端维护参照完整性。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-05-12
    • 1970-01-01
    • 1970-01-01
    • 2017-05-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多