使用主键约束的查询优化

捕获表中字段之间的关系的主键约束可以帮助用户和工具了解数据中的关系。 本文包含的示例演示如何将主键与用于优化某些常见查询类型的 RELY 选项结合使用。

添加主键约束

可以在表创建语句中添加主键约束,如以下示例所示,或使用 ADD CONSTRAINT 子句向表添加约束。

CREATE TABLE customer (
  c_customer_sk int,
  PRIMARY KEY (c_customer_sk)
  ...
  )

在此示例中,c_customer_sk 是客户 ID 密钥。 主键约束指定每个客户 ID 值在表中应是唯一的。 Azure Databricks 不会强制实施主键约束。 可以通过现有数据管道或 ETL 验证它们。 请参阅使用增量实时表管理数据质量,了解有关流式处理表和具体化视图的工作期望。 请参阅 Azure Databricks 上的约束,了解如何处理 Delta 表的约束。

备注

用户负责确保是否满足约束。 依赖于未被满足的约束可能会导致查询结果不正确。

使用 RELY 启用优化

当知道主键约束有效时,可以通过使用 RELY 选项指定该约束来启用基于约束的优化。 有关完整语法,请参阅 ADD CONSTRAINT 子句

RELY 选项允许 Azure Databricks 利用约束重写查询。 只有在 ADD CONSTRAINT 子句或 ALTER TABLE 语句中指定了 RELY 选项时,才能执行以下优化。

使用 ALTER TABLE,可以修改表的主键来包含 RELY 选项,如以下示例所示。


ALTER TABLE
  customer DROP PRIMARY KEY;
ALTER TABLE
  customer
ADD
  PRIMARY KEY (c_customer_sk) RELY;

优化示例

以下示例扩展了上一个示例,该示例创建一个 customer 表,其中 c_customer_sk 是一个名为 PRIMARY KEY 且指定了 RELY 选项的唯一标识符。

示例 1:消除不必要的聚合

下面显示了将 DISTINCT 操作应用于主键的查询。

SELECT
  DISTINCT c_customer_sk
FROM
  customer;

由于 c_customer_sk 列是已验证 PRIMARY KEY 约束,因此该列中的所有值都是唯一的。 指定 RELY 选项后,Azure Databricks 可以通过不执行 DISTINCT 操作来优化查询。

示例 2:消除不必要的联接

以下示例演示了一个查询,其中 Azure Databricks 可以消除不必要的联接。

查询联接事实数据表,含有维度表 customerstore_sales。 它执行左外部联接,因此查询结果包括 store_sales 表中的所有记录,以及 customer 表中匹配的记录。 如果 customer 表中没有匹配的记录,查询结果将显示 c_customer_sk 列的 NULL 值。

SELECT
  SUM(ss_quantity)
FROM
  store_sales ss
  LEFT JOIN customer c ON ss.customer_sk = c.c_customer_sk;

若要了解为什么不需要此联接,请考虑查询语句。 它只需要 store_sales 表中的 ss_quantity 列。 customer 表在其主键上联接,因此 store_sales 的每一行在 customer 中最多匹配一行。 由于操作是外部联接,因此将保留 store_sales 表中的所有记录,因此该联接不会更改该表中的任何数据。 无论这些表是否联接在一起,SUM 聚合都是相同的。

将主键约束与 RELY 一起使用可让查询优化器获得消除联接所需的信息。 优化查询如下所示:

SELECT
  SUM(ss_quantity)
FROM
  store_sales ss

后续步骤

请参阅查看实体关系图,了解如何在目录资源管理器 UI 中浏览主键和外键关系。