什么叫索引
数据库索引
数据库索引分为:
单例索引
复合索引
如果某表的某个字段有主键约束和唯一约束,则Oracle会在会在相应的约束列上建立唯一索引,建立数
据库索引的目的是为了加快查询速度。
数据库索引建立的原则:
1.索引应该建立在where子句经常用到的列上,如果某个大表经常用到某个字段进行查询,并且检
索行数小于总表行数的5%(检索行数非常多时),则应该考虑建立索引。
2.对于两表连接的字段,应该建立索引,如果经常在某个表上进行Order by 也应该添加索引
3.字段较少的表则尽量减少索引的建立。
建立索引的优缺点
创建索引可以加快查询速度。但是当进行DML操作的时候,会更新索引,执行DML操作的效率会降低,因此
并不是索引越多越好,创建索引时也应该权衡利弊。
创建索引
创建单例索引
create index <index_name>(索引名称) on <table_name>(字段名)。
创建复合索引
create index i_dephon_jop on emp(dephon,jop)(给emp表中的dephon和jop字段建立索引);
此时:
select * from emp where dephon = 66 and jop = ‘销售部’;(走的是索引)
select * from emp where dephon = 66 or jop = ‘销售部’;(不走索引)
select * from emp where dephon = 66;(走索引)
select * from emp where jop = ‘销售部’;(不走索引)
可知,当进行复合索引的创建时在where子句中会以第一个字段为基准,后面以and连接,会都走索引,以or连接,不会走索引(默认第二个字段不走索引,则全局不走索引)。
从sql执行顺序到优化
sql执行顺序
1.from子句组装来组不同数据源的数据;
2.where 子句基于指定条件对记录进行筛选;
3.group by 将数据划分为多个分组;
4.使用聚合函数进行计算;
5.使用having子句筛选分组(用法和where用法相同,但是如果是聚合函数则必须使用having子句);
6.计算所有表达式;
7.select 字段;
8.使用order by 字段对字段集进行排序;
sql语句不同于其他编程语言的明显特征是处理代码的顺序,第一个被处理的的子句是from,而不是第一次
出现的select,一个完整的sql的执行顺序应该是:
from --> on --> join --> where -->group --> with{cube|rollup} --> having
--> select --> distinct(去重)--> order by
扩展:
with{cube|rollup} :该子句的使用是在group by 后使用的。可以理解为,先按照一定的规律产生多种分
组,然后按照多种分组进行数据统计(统计的数据是求和、求最大值、求平均值等就取决于select后的
聚合函数),因此要搞懂group by 后跟with{cube|rollup}的用法主要需要搞懂它是如何按照一定的规则
产生多种分组的,另group后跟with{cube|rollup}子句所返回的结果集,可以理解为各个分组所产生的结
果集的并集,并且没有去掉重复的数据
sql优化
为什么进行sql优化:在进行查询操作时,oracle使用索引来快速地遍历数据库表,sql优化器主要时根据定义地索引来提高性能的。但是,如果在sql语句的where子句中写的sql代码不合理,就会造成sql优化器忽略索引而进行全局扫描,一般的sql也就是我们所谓的劣质sql语句,对于海量数据的查询,劣质sql语句和优质sql语句的查询速度相差可达到数百倍,由此可见,一个系统的实现不仅仅是简单的实现功能就可以的,而是要写出高质量的sql语句,提高系统的可用性。
常见的优化规则:
1.表连接数量
连接的表越多,性能越差;
可能的话,将连接拆分成若干过程逐个去执行;
先执行可以显著减少数据量的连接,既降低了复杂度,也能够按照预期执行;
外连接效果较差,因为必须对左右表进行扫描;
尽量使用inner join(join)查询;
2.使用临时表
3.sql编写注意事项
null列:null列使用索引是没有意义的,任何包含null值的列都不会被包含在索引索引中,因此where
中的is null 或is not null的语句优化器是不允许使用索引的。
like:通配符(%)出现在首位时,是无法使用索引的,反之可以。
order by:order by子句中不要使用非索引列或嵌套表达式,这样会导致性能降低。
尽量的使用exists来代替in:not in 是最低效的,因为要对子查询的表进行全表扫描,可以考虑使用
外连接或not exists
尽量的使用union来代替or:在索引列上使用or会导致全表扫描。
is null 或 is not null :如果列为空,避免使用索引。对于多个列使用索引,起码要保证有个列不为
空,对于多列索引,只用访问到第一列才会启动索引,如果访问到后面的列则会使用全表扫描。
union和union all:union具有去重效果,增加了计算的时间。union all不需要去重,会包含相同的
记录,因此在相同功能下,推荐使用union all操作。
尽量避免在where子句的表达式后使用运算符,可将直接将运算结果写入表达式后面。
避免在where子句中使用!=或<>而对于<、<=、=、>=、>、between and,数据库才会使用索引