外键列上是否需要索引
上一篇 / 下一篇 2009-02-16 21:34:13 / 个人分类:ORACLE
其实这个问题应该算是老生常谈了。这两天看concept看到这里,于是就在说说这个问题。
外键列上缺少索引会带来两个问题,限制并发性、影响性能。而这两个问题中的任意一个都可能会造成严重性能问题。
无论是Oracle的官方文档,还是在Tom的书中都说明了两种情况下可以忽略外键上的索引。其实我认为不需要那么麻烦,与增加一个索引所带来的性能开销和磁盘空间开销相比,确实索引可能引发的问题要严重得多。因此,我会选择在所有的外键列上添加索引,虽然可能导致创建了部分多余的索引,但是这样相除了外键约束由于确实索引所带来的性能问题和并发性问题。
如果外键列上缺少索引,从主表关联子表的查询就只能对子表选择全表扫描的查询,这是显而易见的问题:
SQL> CREATE TABLE T_P (ID NUMBER, NAME VARCHAR2(30));
表已创建。
SQL> ALTER TABLE T_P ADD PRIMARY KEY (ID);
表已更改。
SQL> CREATE TABLE T_C (ID NUMBER, FID NUMBER, NAME VARCHAR2(30));
表已创建。
SQL> ALTER TABLE T_C ADD CONSTRAINT FK_T_CITPUB个人空间e#H3Bk:DW
Y
2 FOREIGN KEY (FID)
QMTgL
m(F~0 3 REFERENCES T_P (ID);
表已更改。
SQL> INSERT INTO T_P SELECT ROWNUM, TABLE_NAME FROM ALL_TABLES;
已创建884行。
SQL> INSERT INTO T_C SELECT ROWNUM, MOD(ROWNUM, 884) + 1, OBJECT_NAME
'n{{+Nd#m0 2 FROM ALL_OBJECTS;
已创建30339行。
SQL> COMMIT;
提交完成。
SQL> SELECT A.ID, A.NAME, B.NAMEITPUB个人空间%iJf+Djr
2 FROM T_P A, T_C B
wvdp
L E%b7Jv0 3 WHERE A.ID = B.FIDITPUB个人空间gs5{-i[]D5y3m k8L
4 AND A.ID = 880;
ID NAME NAME
MVB,r.a8z*iR0---------- ------------------------------ ------------------------------
$p}G~H'b.O0 880 T_COMPRESS /eb2b6b5_Options1ITPUB个人空间ut EumuZ
880 T_COMPRESS DATE
SbT8~(\#_
z/N0 880 T_COMPRESS DEF$_SCHEDULEITPUB个人空间8k"KS]|n4y7[6C
880 T_COMPRESS GV_$SESSION_EVENTITPUB个人空间m
E@{'wO$gV
.ITPUB个人空间&f2y
f#nR!?e2J
pOb
.
L4Hb
iI
T6G4@0.ITPUB个人空间;Q:A`$X#sXP
880 T_COMPRESS sun/io/ByteToCharCp1251
iS8m m)c`q}0 880 T_COMPRESS /5ba
880 T_COMPRESS USER_INDEXTYPES
已选择34行。
ITPUB个人空间?'m
Xh6e+Vw
执行计划
9Yln p*qw4@
y0----------------------------------------------------------
(~#^7Mv-on0ul0 0 SELECT STATEMENT ptimizer=CHOOSE
`5R$gv1l3_ `@/OS W0 1 0 MERGE JOINITPUB个人空间o%q/}4G| J
2 1 TABLE ACCESS (BY INDEX ROWID) OF 'T_P'
}3|B;\u,~"PO0 3 2 INDEX (UNIQUE SCAN) OF 'SYS_C002964' (UNIQUE)ITPUB个人空间
j(WO~3K_&~S
4 1 FILTER
[:Z%@d%Q6]k'lo0 5 4 TABLE ACCESS (FULL) OF 'T_C'
ITPUB个人空间i]7u+R z3\
统计信息ITPUB个人空间!I0d
Bz$l-DVR
----------------------------------------------------------ITPUB个人空间 cq`3S_`:z
0 recursive calls
~3I&Qxvb0 0 db block getsITPUB个人空间)R$e ^@-iCD
190 consistent gets