Oracle在哪些情况下会自动创建索引?
Posted
技术标签:
【中文标题】Oracle在哪些情况下会自动创建索引?【英文标题】:In which cases will Oracle create indexes automatically? 【发布时间】:2011-01-10 09:04:32 【问题描述】:据我所知 (this page),Oracle 会自动为每个 UNIQUE 或 PRIMARY KEY 声明创建一个索引。这是在 Oracle 中自动创建索引的完整案例列表吗?
【问题讨论】:
【参考方案1】:我将尝试整合给出的答案并使其成为社区 wiki。 因此,对于这种情况,Oracle 会自动创建索引:
-
APC:用于主键和唯一键,除非此类索引已存在。
APC:用于 LOB 存储和 XMLType。
Gary:对于带有嵌套表的表。
Jim Hudson:用于物化视图。
【讨论】:
“LOB 存储”情况可能还会导致其他复杂数据类型的索引。虽然我没有测试过这个。我希望 Oracle Spatial、Oracle Text 等创建索引。 这是社区维基。如果你想添加任何东西,你可以编辑这个答案。【参考方案2】:首先,当我们创建主键或唯一键时,Oracle 并不总是创建索引。如果该列上已经有索引,它将使用它来代替...
SQL> create table t23 (id number not null)
2 /
Table created.
SQL> create index my_manual_idx on t23 ( id )
2 /
Index created.
SQL> select index_name from user_indexes
2 where table_name = 'T23'
3 /
INDEX_NAME
------------------------------
MY_MANUAL_IDX
SQL>
...注意MY_MANUAL_IDX
不是唯一索引;没关系……
SQL> alter table t23
2 add constraint t23_pk primary key (id) using index
3 /
Table altered.
SQL> select index_name from user_indexes
2 where table_name = 'T23'
3 /
INDEX_NAME
------------------------------
MY_MANUAL_IDX
SQL> drop index my_manual_idx
2 /
drop index my_manual_idx
*
ERROR at line 1:
ORA-02429: cannot drop index used for enforcement of unique/primary key
SQL>
还有一种情况Oracle会自动创建索引:LOB存储....
SQL> alter table t23
2 add txt clob
3 lob (txt) store as basicfile t23_txt (tablespace users)
4 /
Table altered.
SQL> select index_name from user_indexes
2 where table_name = 'T23'
3 /
INDEX_NAME
------------------------------
MY_MANUAL_IDX
SYS_IL0000556081C00002$$
SQL>
编辑
数据库将 XMLType 视为与其他 LOB 相同...
SQL> alter table t23
2 add xmldoc xmltype
3 /
Table altered.
SQL> select index_name from user_indexes
2 where table_name = 'T23'
3 /
INDEX_NAME
------------------------------
MY_MANUAL_IDX
SYS_IL0000556081C00002$$
SYS_IL0000556081C00004$$
SQL>
【讨论】:
我已经有几年没有做Oracle了,但我似乎记得Oracle可以使用复合索引,如果设置为UNIQUE(或PRIMARY KEY?)的字段是第一个字段。我可能记错了,或者它可能自 8i 线以来已经改变,所以我建议测试它是否有用。 (避免有额外的索引并在写入中受到打击) 一个例子总是很容易理解。 如果你的表已经有索引但没有主键,我认为这不是一个好主意。这是你开场白中的假设。我从未见过与在创建表时创建的主键不同的情况,而且我不明白为什么应该以不同的方式完成它,即使从技术上讲你可以。唯一键是另外一回事......但实际上,它也应该在创建表时设置。因此,它上面会存在一些索引。 @tvCa - 显然您没有在数据仓库等工作环境中加载大量数据的经验。有时删除唯一约束但保留基础索引可能很有用。这需要我们在预先创建的非唯一索引上构建唯一约束。这不是常见的情况,但也不是不合理的情况。【参考方案3】:不,我们越来越近了,但这还不是一个完整的列表。
创建物化视图时还会自动创建一个索引,因为 Oracle 在进行快速刷新时需要能够快速识别行。对于基于 rowid 的物化视图,它使用 I_SNAP$_tablename。对于主键实体化视图,它使用原始 PK 名称,并根据需要进行修改以使其唯一。
create materialized view testmv
refresh force with rowid
as select * from dual;
select index_name from user_indexes where table_name = 'TESTMV';
Index Name
--------------
I_SNAP$_TESTMV
【讨论】:
【参考方案4】:另外一个,如果你创建一个带有嵌套表的表,你会得到一个自动创建的索引。一般来说,基于对象的存储可以做到这一点,因为可以创建隐藏表。
我认为基于模式的 XMLTypes 也可以。
【讨论】:
【参考方案5】:是的,这是完整的列表。 Oracle 自动为每个 UNIQUE 或 PRIMARY KEY 声明创建一个索引。
【讨论】:
根据accepted answer,这不是完整的列表...以上是关于Oracle在哪些情况下会自动创建索引?的主要内容,如果未能解决你的问题,请参考以下文章