Oracle索引详解

索引

类似于书的目录,提高查询效率。

创建索引语法:

 CREATE [UNIQUE] [BITMAP] INDEX 索引名称 ON 表名(字段,[字段,..,..]);
 名词解释:
     UNIQUE 唯一索引
     BITMAP 位图索引
     默认不写 UNIQUE 和 BITMAP 为普通索引
     表名后面写多个字段为复合索引
     在字段加函数为函数索引
     
 注意:当给表中字段添加主键约束或唯一约束时会自动生成一个索引

示例1:创建主键约束和唯一约束

1)创建INDEX_TB

 CREATE TABLE INDEX_TB(
        ID NUMBER,
        NAME VARCHAR2(30),
        SEX CHAR(2),
        AGE NUMBER(3)
 );

2)给INDEX_TB表中添加数据

 BEGIN
   FOR V IN 1..10000 LOOP
     IF MOD(V,2) = 1 THEN
       INSERT INTO INDEX_TB VALUES(V,CHR(FLOOR(DBMS_RANDOM.value(45000,60000)))||CHR(FLOOR(DBMS_RANDOM.value(45000,60000))),'男',FLOOR(DBMS_RANDOM.value(18,100)));
     ELSE
       INSERT INTO INDEX_TB VALUES(V,CHR(FLOOR(DBMS_RANDOM.value(45000,60000)))||CHR(FLOOR(DBMS_RANDOM.value(45000,60000))),'女',FLOOR(DBMS_RANDOM.value(18,100)));      
     END IF;
   END LOOP;
 END;

3)给INDEX_TB表中的ID列添加主键

 alter TABLE index_tb add constraint pk_id primary key(ID);

当我给表中添加主键约束时,会发现表中已经有索引了。

4)删除INDEX_TB表中的主键约束,为其添加唯一约束

 alter table index_tb drop constraint PK_ID; -- 删除主键约束
 alter table index_tb add constraint unique_id unique(ID); -- 添加唯一约束

这个时候我们再次查看表就发现,表中已经默认生成索引了

示例2:创建普通索引

 CREATE INDEX PT_IND ON INDEX_TB(NAME);
 什么叫普通索引?
     任何列都可以创建        

示例3:创建唯一索引

 CREATE UNIQUE INDEX u_ind ON INDEX_TB(AGE);

如上图所示:

当我们需要给表中某个列添加唯一索引时,那么该列的值中不能出现重复值,否则添加失败;同理,当我们给某个列添加上唯一索引时,那么该列也会被添加上唯一约束,以后该列就不能在添加重复数据了。

示例4:创建位图索引

 CREATE BITMAP INDEX m_ind ON INDEX_TB(sex);

什么是位图索引?

位图索引适合建立在基数小的列,例如:性别、地区、婚姻状况等列。

示例5:创建复合索引

CREATE UNIQUE INDEX fh_ind ON INDEX_TB(id,name,sex);

注意:

在使用复合索引时一定要保证最左原则,也就是说当我在查询时,我where条件中没有id列,而是其他俩个列则索引失效。

验证:

EXPLAIN PLAN FOR
SELECT * FROM INDEX_TB WHERE SEX = '男';
SELECT * FROM TABLE(DBMS_XPLAN.display);

如上图所示,该语句并没有走我创建的复合索引(fh_ind),如果我将where条件换成id则不一样,测试如下显示:

EXPLAIN PLAN FOR
SELECT * FROM INDEX_TB WHERE ID = 888;
SELECT * FROM TABLE(DBMS_XPLAN.display);

示例6:函数索引

已知在示例2中我已经创建了普通索引,但是,不管什么索引,当我们在索引列上使用函数时,索引就会失效。测试如下:

EXPLAIN PLAN FOR
SELECT * FROM INDEX_TB WHERE ASCII(NAME) = 48615;
SELECT * FROM TABLE(DBMS_XPLAN.display);

如上图所示,我在示例2中为name列创建的普通索引pt_ind没有被使用。其原因是因为我在索引列上使用了函数。但是在实际工作中,我们有时候必须要使用函数,该怎么办呢?我们可以为其创建一个函数索引。如下:

CREATE INDEX HS_ind ON INDEX_TB(ASCII(NAME)); -- 为name列添加函数索引
-- 再次执行上一条代码
EXPLAIN PLAN FOR
SELECT * FROM INDEX_TB WHERE ASCII(NAME) = 48615;
SELECT * FROM TABLE(DBMS_XPLAN.display);

如上图所示,当我再次查看执行计划时,发现该语句在执行是使用了索引。

说白了,函数索引就是基于对表中列计算后的结果创建索引。

  • 0
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值