0

0

oracle有哪些索引

青灯夜游

青灯夜游

发布时间:2022-04-18 17:18:09

|

9041人浏览过

|

来源于php中文网

原创

oracle的索引类型有:非唯一索引、唯一索引、位图索引、局部有前缀分区索引、局部无前缀分区索引、全局有前缀分区索引、散列分区索引、基于函数的索引。索引需在表中插入数据后创建,唯一索引可用“create unique index”语句创建。

oracle有哪些索引

本教程操作环境:Windows7系统、Oracle 11g版、Dell G3电脑。

什么是索引?

  • 索引是建立在表的一列或多个列上的辅助对象,目的是加快访问表中的数据;
  • Oracle存储索引的数据结构是B*树(平衡树),位图索引也是如此,只不过是叶子节点不同B*数索引;
  • 索引由根节点、分支节点和叶子节点组成,上级索引块包含下级索引块的索引数据,叶节点包含索引数据和确定行实际位置的rowid。

索引说明

1)索引是数据库对象之一,用于加快数据的检索,类似于书籍的索引。在数据库中索引可以减少数据库程序查询结果时需要读取的数据量,类似于在书籍中我们利用索引可以不用翻阅整本书即可找到想要的信息。

2)索引是建立在表上的可选对象;索引的关键在于通过一组排序后的索引键来取代默认的全表扫描检索方式,从而提高检索效率

3)索引在逻辑上和物理上都与相关的表和数据无关,当创建或者删除一个索引时,不会影响基本的表;

4)索引一旦建立,在表上进行DML操作时(例如在执行插入、修改或者删除相关操作时),oracle会自动管理索引,索引删除,不会对表产生影响

5)索引对用户是透明的,无论表上是否有索引,sql语句的用法不变

6)oracle创建主键时会自动在该列上创建索引

使用索引的目的:

  • 加快查询速度
  • 减少I/O操作
  • 消除磁盘排序(索引能加快排序速度)

何时使用索引:

  • 查询返回的记录数 排序表<40%,对非排序表<7%
  • 表的碎片较多(频繁增加、删除)

索引的种类

  • 非唯一索引(最常用)
  • 唯一索引
  • 位图索引
  • 局部有前缀分区索引
  • 局部无前缀分区索引
  • 全局有前缀分区索引
  • 散列分区索引
  • 基于函数的索引

管理索引的准则

  • 在表中插入数据后创建索引
  • 在用SQL*Loader或import工具插入或装载数据后,建立索引比较有效;

索引正确的表和列

  • 经常检索排序大表中40%或非排序表7%的行,建议建索引;
  • 为了改善多表关联,索引列用于联结;
  • 列中的值相对比较唯一;
  • 取值范围(大:B*树索引,小:位图索引);
  • Date型列一般适合基于函数的索引;
  • 列中有许多空值,不适合建立索引

为性能而安排索引列

  • 经常一起使用多个字段检索记录,组合索引比单索引更有效;
  • 把最常用的列放在最前面,例:dx_groupid_serv_id(groupid,serv_id),在where条件中使用groupidgroupid,serv_id,查询将使用索引,若仅用到serv_id字段,则索引无效;

合并/拆分不必要的索引。

限制每个表索引的数量

  • 一个表可以有几百个索引(你会这样做吗?),但是对于频繁插入和更新表,索引越多系统CPU,I/O负担就越重;

  • 建议每张表不超过5个索引。

删除不再需要的索引

  • 索引无效,集中表现在该使用基于函数的索引或位图索引,而使用了B*树索引;

  • 应用中的查询不使用索引;

  • 重建索引之前必须先删除索引,若用alter index … rebuild重建索引,则不必删除索引。

索引数据块空间使用

  • 创建索引时指定表空间,特别是在建立主键时,应明确指定表空间;
  • 合理设定pctfress,注意:不能给索引指定pctused;
  • 估计索引的大小和合理地设置存储参数,默认为表空间大小,或initial与next设置成一样大。

考虑并行创建索引

  • 对大表可以采用并行创建索引,在并行创建索引时,存储参数被每个查询服务器进程分别使用,例如:initial1M,并行度为8,则创建索引期间至少要消耗8M空间;

考虑用nologging创建索引

  • 对大表创建索引可以使用nologging来减少重做日志;
  • 节省重做日志文件的空间;
  • 缩短创建索引的时间;
  • 改善了并行创建大索引时的性能。

怎样建立最佳索引?

明确地创建索引

create index index_name on table_name(field_name)
  tablespace tablespace_name
  pctfree 5
  initrans 2
  maxtrans 255
  storage
  (
  minextents 1
  maxextents 16382
  pctincrease 0
  );

创建基于函数的索引:

常用与UPPER、LOWER、TO_CHAR(date)等函数分类上,例:

create index idx_func on emp (UPPER(ename)) tablespace tablespace_name;

创建位图索引:

对基数较小,且基数相对稳定的列建立索引时,首先应该考虑位图索引,例:

create bitmap index idx_bitm on class (classno) tablespace tablespace_name;

明确地创建唯一索引

可以用create unique index语句来创建唯一索引,例:

create unique index dept_unique_idx on dept(dept_no) tablespace idx_1;

创建与约束相关的索引

可以用using index字句,为与uniqueprimary key约束相关的字段创建索引,例如:

alter table table_name
  add constraint PK_primary_keyname primary key (field_name)
  using index tablespace tablespace_name;

如何创建局部分区索引

  • 基础表必须是分区表;
  • 分区数量与基础表相同;
  • 每个索引分区的子分区数量与相应的基础表分区相同;
  • 基础表的子分区中的行的索引项,被存储在该索引的相应的子分区中,例如:
  Create Index TG_CDR04_SERV_ID_IDX On TG_CDR04(SERV_ID)
  Pctfree 5  Tablespace TBS_AK01_IDX
  Storage (
  MaxExtents 32768  PctIncrease 0  FreeLists 1  FreeList Groups 1  )
  local  /

如何创建范围分区的全局索引

基础表可以是全局表和分区表。

create index idx_start_date on tg_cdr01(start_date)
  global partition by range(start_date)
  (partition p01_idx vlaues less than (‘0106’)
  partition p01_idx vlaues less than (‘0111’)
  …
  partition p01_idx vlaues less than (‘0401’ ))
  /

  重建现存的索引
  重建现存的索引的当前时刻不会影响查询;

  重建索引可以删除额外的数据块;
  提高索引查询效率;

AssemblyAI
AssemblyAI

转录和理解语音的AI模型

下载
alter index idx_name rebuild nologging;

  对于分区索引:

alter index idx_name rebuild partition partiton_name nologging;

要删除索引的原因

  • 不再需要的索引;
  • 索引没有针对其相关的表所发布的查询提供所期望的性能改善;
  • 应用没有用该索引来查询数据;
  • 该索引无效,必须在重建之前删除该索引;
  • 该索引已经变的太碎了,必须在重建之前删除该索引;
  • 语句:<br> drop index idx_name; <br> drop index idx_name drop partition partition_name; <br>

建立索引的代价

基础表维护时,系统要同时维护索引,不合理的索引将严重影响系统资源,主要表现在CPU和I/O上;

插入、更新、删除数据产生大量db file sequential read锁等待;

一个表中有几百万条数据,对某个字段加了索引,但是查询时性能并没有什么提高,这主要可能是oracle的索引限制造成的。

oracle的索引有一些索引限制,在这些索引限制发生的情况下,即使已经加了索引,oracle还是会执行一次全表扫描,查询的性能不会比不加索引有所提高,反而可能由于数据库维护索引的系统开销造成性能更差。

扩展知识:常见的索引限制问题

1、使用不等于操作符(<>, !=)

下面这种情况,即使在列dept_id有一个索引,查询语句仍然执行一次全表扫描

select * from dept where staff_num <> 1000;

但是开发中的确需要这样的查询,难道没有解决问题的办法了吗?

有!

通过把用 or 语法替代不等号进行查询,就可以使用索引,以避免全表扫描:上面的语句改成下面这样的,就可以使用索引了。

select * from dept shere staff_num < 1000 or dept_id > 1000;

2、使用 is null 或 is not null

使用 is nullis nuo null也会限制索引的使用,因为数据库并没有定义null值。如果被索引的列中有很多null,就不会使用这个索引(除非索引是一个位图索引,关于位图索引,会在以后的blog文章里做详细解释)。在sql语句中使用null会造成很多麻烦。

解决这个问题的办法就是:建表时把需要索引的列定义为非空(not null)

3、使用函数

如果没有使用基于函数的索引,那么where子句中对存在索引的列使用函数时,会使优化器忽略掉这些索引。下面的查询就不会使用索引:

select * from staff where trunc(birthdate) = '01-MAY-82';

但是把函数应用在条件上,索引是可以生效的,把上面的语句改成下面的语句,就可以通过索引进行查找。

select * from staff where birthdate < (to_date('01-MAY-82') + 0.9999);

4、比较不匹配的数据类型

比较不匹配的数据类型也是难于发现的性能问题之一。下面的例子中,dept_id是一个varchar2型的字段,在这个字段上有索引,但是下面的语句会执行全表扫描。

select * from dept where dept_id = 900198;

这是因为oracle会自动把where子句转换成to_number(dept_id)=900198,就是3所说的情况,这样就限制了索引的使用。把SQL语句改为如下形式就可以使用索引

select * from dept where dept_id = '900198';

5、使用like子句

使用like子句查询时,数据需要把所有的记录都遍历来进行判断,索引不能发挥作用,这种情况也要尽量避免。

Like 的字符串中第一个字符如果是‘%’则用不到索引

Column1 like ‘aaa%’ 是可以的
Column1 like ‘%aaa%’用不到

6、使用IN

尽管In写法要比exists简单一些,exists一般来说性能要比In要高的多 

In还是用Exists的时机 

当in的集合比较小的时候,或者用Exists无法用到选择性高的索引的时候,用In要好,否则就要用Exists
例:

select count(*) from person_info where xb in (select xb_id from dic_sex);

Select count(*) from n_acntbasic a where shbxdjm =:a and exists(select 1 from person_info where pid=a.pid and …);

Select * from person_info where zjhm=3101….;--将会对person_info全表扫描

Select * from person_info where zjhm =‘3101…’;--才能用到索引

假定TEST表的dt字段是date类型的并且对dt建了索引。
如果要查‘20041010’一天的数据.下面的方法用不到索引

Select * from test where to_char(dt,’yyyymmdd’) =‘20041010’;

而以下将会用到索引。

select * from test where dt >=to_date(‘20041010’,’yyyymmdd’) and dt < to_date(‘20041010’,’yyyymmdd’) + 1

7、如果能不用到排序,则尽量避免排序。

用到排序的情况有
集合操作。Union ,minus ,intersect等,注:union all 是不排序的。

Order byGroup byDistinctIn

有时候也会用到排序
确实要排序的时候也尽量要排序小数据量,尽量让排序在内存中执行,有文章说,内存排序的速度是硬盘排序的1万倍。

在排序的字段上创建索引,让排序在内存中执行,加快排序速度。

8、在基于CBO的优化器(花费)下,表的统计数据过期。也可能导致不使用索引。

解决:执行表分析。获取表的最新信息。

9、获取的数据量过大,全部扫描效率更高

10、索引字段的值分散率太低,值太集中,如类型字段都是1,2, 状态类型Y-有效/N-无效。这类型的字段最好别建索引。

尽管在这些字段上建立了索引,但对全表数据区分度不大。最后还是会全表扫描。

推荐教程:《Oracle教程

热门AI工具

更多
DeepSeek
DeepSeek

幻方量化公司旗下的开源大模型平台

豆包大模型
豆包大模型

字节跳动自主研发的一系列大型语言模型

WorkBuddy
WorkBuddy

腾讯云推出的AI原生桌面智能体工作台

腾讯元宝
腾讯元宝

腾讯混元平台推出的AI助手

文心一言
文心一言

文心一言是百度开发的AI聊天机器人,通过对话可以生成各种形式的内容。

讯飞写作
讯飞写作

基于讯飞星火大模型的AI写作工具,可以快速生成新闻稿件、品宣文案、工作总结、心得体会等各种文文稿

即梦AI
即梦AI

一站式AI创作平台,免费AI图片和视频生成。

ChatGPT
ChatGPT

最最强大的AI聊天机器人程序,ChatGPT不单是聊天机器人,还能进行撰写邮件、视频脚本、文案、翻译、代码等任务。

相关专题

更多
TypeScript类型系统进阶与大型前端项目实践
TypeScript类型系统进阶与大型前端项目实践

本专题围绕 TypeScript 在大型前端项目中的应用展开,深入讲解类型系统设计与工程化开发方法。内容包括泛型与高级类型、类型推断机制、声明文件编写、模块化结构设计以及代码规范管理。通过真实项目案例分析,帮助开发者构建类型安全、结构清晰、易维护的前端工程体系,提高团队协作效率与代码质量。

49

2026.03.13

Python异步编程与Asyncio高并发应用实践
Python异步编程与Asyncio高并发应用实践

本专题围绕 Python 异步编程模型展开,深入讲解 Asyncio 框架的核心原理与应用实践。内容包括事件循环机制、协程任务调度、异步 IO 处理以及并发任务管理策略。通过构建高并发网络请求与异步数据处理案例,帮助开发者掌握 Python 在高并发场景中的高效开发方法,并提升系统资源利用率与整体运行性能。

89

2026.03.12

C# ASP.NET Core微服务架构与API网关实践
C# ASP.NET Core微服务架构与API网关实践

本专题围绕 C# 在现代后端架构中的微服务实践展开,系统讲解基于 ASP.NET Core 构建可扩展服务体系的核心方法。内容涵盖服务拆分策略、RESTful API 设计、服务间通信、API 网关统一入口管理以及服务治理机制。通过真实项目案例,帮助开发者掌握构建高可用微服务系统的关键技术,提高系统的可扩展性与维护效率。

276

2026.03.11

Go高并发任务调度与Goroutine池化实践
Go高并发任务调度与Goroutine池化实践

本专题围绕 Go 语言在高并发任务处理场景中的实践展开,系统讲解 Goroutine 调度模型、Channel 通信机制以及并发控制策略。内容包括任务队列设计、Goroutine 池化管理、资源限制控制以及并发任务的性能优化方法。通过实际案例演示,帮助开发者构建稳定高效的 Go 并发任务处理系统,提高系统在高负载环境下的处理能力与稳定性。

59

2026.03.10

Kotlin Android模块化架构与组件化开发实践
Kotlin Android模块化架构与组件化开发实践

本专题围绕 Kotlin 在 Android 应用开发中的架构实践展开,重点讲解模块化设计与组件化开发的实现思路。内容包括项目模块拆分策略、公共组件封装、依赖管理优化、路由通信机制以及大型项目的工程化管理方法。通过真实项目案例分析,帮助开发者构建结构清晰、易扩展且维护成本低的 Android 应用架构体系,提升团队协作效率与项目迭代速度。

99

2026.03.09

JavaScript浏览器渲染机制与前端性能优化实践
JavaScript浏览器渲染机制与前端性能优化实践

本专题围绕 JavaScript 在浏览器中的执行与渲染机制展开,系统讲解 DOM 构建、CSSOM 解析、重排与重绘原理,以及关键渲染路径优化方法。内容涵盖事件循环机制、异步任务调度、资源加载优化、代码拆分与懒加载等性能优化策略。通过真实前端项目案例,帮助开发者理解浏览器底层工作原理,并掌握提升网页加载速度与交互体验的实用技巧。

105

2026.03.06

Rust内存安全机制与所有权模型深度实践
Rust内存安全机制与所有权模型深度实践

本专题围绕 Rust 语言核心特性展开,深入讲解所有权机制、借用规则、生命周期管理以及智能指针等关键概念。通过系统级开发案例,分析内存安全保障原理与零成本抽象优势,并结合并发场景讲解 Send 与 Sync 特性实现机制。帮助开发者真正理解 Rust 的设计哲学,掌握在高性能与安全性并重场景中的工程实践能力。

230

2026.03.05

PHP高性能API设计与Laravel服务架构实践
PHP高性能API设计与Laravel服务架构实践

本专题围绕 PHP 在现代 Web 后端开发中的高性能实践展开,重点讲解基于 Laravel 框架构建可扩展 API 服务的核心方法。内容涵盖路由与中间件机制、服务容器与依赖注入、接口版本管理、缓存策略设计以及队列异步处理方案。同时结合高并发场景,深入分析性能瓶颈定位与优化思路,帮助开发者构建稳定、高效、易维护的 PHP 后端服务体系。

619

2026.03.04

AI安装教程大全
AI安装教程大全

2026最全AI工具安装教程专题:包含各版本AI绘图、AI视频、智能办公软件的本地化部署手册。全篇零基础友好,附带最新模型下载地址、一键安装脚本及常见报错修复方案。每日更新,收藏这一篇就够了,让AI安装不再报错!

173

2026.03.04

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
SQL 教程
SQL 教程

共61课时 | 4.3万人学习

Java 教程
Java 教程

共578课时 | 82.1万人学习

oracle知识库
oracle知识库

共0课时 | 0.6万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号