代码之家  ›  专栏  ›  技术社区  ›  Gandalf

这里是否适合使用索引组织表?

  •  3
  • Gandalf  · 技术社区  · 16 年前

    我最近读到了关于Oracle索引组织表(IOT)的文章,但不确定我是否完全理解何时使用它们。我有一张小桌子:

    create table categories 
    (
       id        VARCHAR2(36),
       group     VARCHAR2(100),
       category  VARCHAR2(100
    )
    create unique index (group, category, id) COMPRESS 2;
    

    id entries 我的常见问题是:

    select e.id, e.time, e.title from entries e, categories c where e.id=c.id AND e.group=? AND c.category=? ORDER by e.time 
    

    由于我基本上是对整个表进行索引,因此将此表创建为IOT是否有意义?

    编辑

    create table entries
    (
       id        VARCHAR2(36),
       time      TIMESTAMP,
       group     VARCHAR2(100),
       title     VARCHAR2(500),
       ....
    )
    
    create index (group, time) compress 1;
    

    不过,我认为我真正的问题并不取决于此。基本上,如果你有一个列数不多的表(本例中为3列),并且你计划在所有三行上放置一个复合索引,那么有什么理由不使用IOT吗?

    4 回复  |  直到 16 年前
        1
  •  1
  •   DCookie    16 年前

    IOT有很多用途,包括在这种情况下,你无论如何都会在所有(或大多数)列上都有一个索引,但只有当你 没有 额外的索引——这个想法是,表本身就是一个索引,所以按照索引的顺序排列列。在你的例子中,你是按id访问类别的,所以把它作为第一列是有意义的。因此,你实际上已经有了一个关于(id、group、category)的索引。我不知道为什么你想在(group、category、id)上添加一个额外的索引。

    SELECT e.id, e.time, e.title
    FROM entries e, categories c
    WHERE e.id=c.id AND e.group=? AND c.category=?
    ORDER by e.time
    

    您正在通过ID连接表,但entries.ID上没有索引,因此查询可能正在进行哈希或排序合并连接。我不介意看到你的系统现在正在做什么的计划来确认。

    NESTED LOOPS
       ACCESS TABLE BY ROWID - ENTRIES
          INDEX RANGE SCAN - (index on ENTRIES.group,time)
       ACCESS TABLE BY ROWID - CATEGORIES
          INDEX RANGE SCAN - (index on CATEGORIES.ID)
    

    由于CATEGORIES的连接在ID上,因此您需要在ID上创建索引;如果你把它做成一个物联网,并把ID列在前面,这可能就足够了。

    我上面展示的计划的性能将取决于有多少行与给定的“组”匹配,即平均“组”的选择性。

        2
  •  1
  •   Jeffrey Kemp    16 年前

    你看过吗 dba-oracle.com asktom.com IOUG , another asktom.com ?

    IOT需要支付罚款,例如插入性能较差

    你能制作原型并比较性能吗?

    此外,也许你可以考虑 hash cluster .

        3
  •  0
  •   David    16 年前

    这里有几件事:

    1. 你提到分页——你考虑过第一行提示吗?
    2. 这是你的索引的顺序吗,以组为第一个字段?如果是这样,我会考虑将移动ID作为第一列,因为不会使用该索引。
    3. 你确定这不是造成缓慢的原因吗?
        4
  •  0
  •   Adrian    16 年前

    您使用的是哪个版本的Oracle? 我假设字段id的表条目上有主键,对吗? 为什么WHERE条件不包括“c.group=e.group”?

    尝试:

    1. 按条件删除订单
    2. category,id)创建唯一索引(id,group,category)
    3. 将表类别重新组织为IOT(组、类别、id)
    4. 将表类别重新组织为IOT(id、组、类别)

    在上述每种情况下使用 EXPLAIN PLAN 审查成本