【问题标题】:index skip scan for 2 value in where clause for second column索引跳过扫描第二列的 where 子句中的 2 个值
【发布时间】:2017-05-16 15:59:09
【问题描述】:

我在(SWcode,cdcardno)上创建了一个索引

然后我运行这个查询:

SELECT cd.*
  FROM KS cd
  where cd.cdcardno in ('6219862012953805')
 ORDER BY cd.ROWID

and oracle 使用索引跳过扫描,这是真的。但是当我运行这个查询时:

SELECT cd.*
  FROM KS cd
  where cd.cdcardno in ('6219861009150391','6219862012953805')
 ORDER BY cd.ROWID

oracle 使用全面扫描。我不明白为什么。

【问题讨论】:

  • 当索引中有两个或多个字段时,oracle 可以选择跳过扫描,并且 oracle 选择“跳过”第一个或多个字段并从较低的字段“扫描”索引索引树。他们所说的直方图和数据分布是真的,但是如果您在 WHERE 子句中只选择一个字段,那么期望跳过扫描是没有意义的。

标签: performance indexing oracle11g sql-tuning


【解决方案1】:

有时,Oracle 在两个执行计划之间摇摆不定,其中一个很糟糕,另一个更糟。创建一个索引,其中cdcardno 在列表中的第一个位置。或者只是翻转当前索引中列的顺序。

【讨论】:

  • 但是为什么会这样呢?我读过,例如,如果我们在第一个查询中为第一列有 4 个不同的值,oracle 将表拆分为 4 个子表,并在每个子表中搜索第二列上的索​​引。是真的吗?如果是,为什么当我为第二列输入两个值时,oracle 不做类似的事情?
  • 可能的解释是直方图。 Oracle 估计,后一个查询将返回更多行。无论如何SKIP SCAN 是“最糟糕”的可能索引用法之一。您真正的问题是,您没有索引,其中 cdcardno 是前导列。
【解决方案2】:

优化器将根据成本生成执行计划。这反过来又基于统计数据。除非您提供一些诊断数据,例如 SQL 监视器报告,否则您将收到的答案将是猜测。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-11-24
    • 2012-03-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-03-13
    • 2015-01-26
    相关资源
    最近更新 更多