【问题标题】:Oracle hint on multiple indexes with multiple join statement使用多个连接语句的多个索引的 Oracle 提示
【发布时间】:2019-07-04 15:28:26
【问题描述】:

我有一个查询如下:

SELECT /*+ INDEX(A T1_IX01) INDEX(A T1_IX02) INDEX(B T2_IX01) INDEX(C T2_IX01)*/
       *
FROM   T1 A
JOIN   T2 B
ON     A.SOURCE = B.C1
JOIN   T2 C
ON     A.TARGET = C.C1;

我需要使用 T1 中的 2 个索引,我使用 SOURCE 列创建,另一个使用 TARGET 列,该列具有与 T2 的 C1 的映射值,该 C1 也被索引。

在当前状态下,它只使用 T1 中的一个索引,该索引被声明为第一个提示,而不是后一个提示。 总而言之,我想将在同一张表上创建的两个不同索引用于两个单独的连接。

为什么以及如何解决这个问题以获得更快的结果?

【问题讨论】:

  • 你不能。您可能可以在多个列上创建一个新索引,包括可能会使用的 a.source 和 a.target。但是,如果我是你,我会避开这些提示,让 Oracle 自己解决。使用索引并不总是好事,全表扫描也不总是坏事。
  • 如果性能可以接受,我会把它留给 oracle 优化器。我使用了提示,因为 Oracle 优化器并不总是提供与您所说的相反的最佳结果,因为我将两个具有数十万个结果的表连接在一起。
  • 统计数据是最新的吗?
  • 你是指什么样的统计数据?

标签: sql oracle query-performance


【解决方案1】:

显然,我已经提示优化器使用散列连接而不是使用创建的索引,然后性能提高了相当高的水平。任何其他想法将不胜感激。

SELECT /*+ use_hash */
       *
FROM   T1 A
JOIN   T2 B
ON     A.SOURCE = B.C1
JOIN   T2 C
ON     A.TARGET = C.C1;

【讨论】:

    【解决方案2】:

    正如@Boneist 所说,让优化器完成工作。

    同样对于任何数据库来说(在大多数情况下)为同一个表使用 2 个索引是没有意义的。一旦你遍历了一个索引,你就已经有了表块的 ROWID。从此块中,您可以获得 all 表的列的值。所以你不需要遍历任何其他索引。

    与其创建两个索引,不如创建一个包含多个列的索引。 根据经验,按方差对索引中的列进行排序。将最有选择性的列放在前面。

    【讨论】:

      猜你喜欢
      • 2021-07-02
      • 1970-01-01
      • 1970-01-01
      • 2013-06-23
      • 2021-11-06
      • 2018-12-16
      • 2013-12-05
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多