表的连接方法
1)from子句中表的顺序
在select语句的from子句中,可以指定多个表的名称。至于表与表之间的先后顺序,如果从查询结果来看,哪个表放在前面都一样,但是如果从查询效率来考虑,表之间的顺序是不能随意的。
一般来说,Oracle的解析器在处理from子句中的表时,是按照从右到左的顺序,也就是说,from子句中最后指定的表将被Oracle首先处理,Oracle将它作为驱动表(Driving Table),并对该表的数据进行排序;之后再扫描倒数第二个表;最后将所有从第二个表中检索出来的记录与第一个表中的合适记录进行合并。
因此,在使用表的连接查询时,建议选择记录行数最少的表作为驱动表,也就是将它作为from子句中的最后一个表。
2)where子句的连接顺序
在执行查询的where子句中,可以指定多个检索条件。Oracle采用自右向左(自下向上)的顺序解析where子句,根据这个顺序,表之间的连接应该写在其他where条件之前,将可以过滤掉最大数量记录的条件写在where子句的末尾。
有效使用索引
虽然使用索引能提高查询效率,但是也必须注意使用索引所付出的的代价。索引需要空间来存储;需要定期维护;每当有记录增减或索引列被修改时,索引本身也会被修改。这意味着针对每条记录的insert、update和delete操作,都需要更多的磁盘I/O。因为索引需要额外的存储空间和处理操作,所以那些不必要的索引反而会影响查询效率。因此,有效地使用索引是很有必要的。
1) 创建索引的基本原则
创建索引时,需要对相应的表认真分析,主要从以下几个基本原则进行考虑:
- 对于经常以查询关键字为基础的表,并且该表中的数据行是均匀分布的;
- 以查询关键字为基础,表中的数据行随机排序;
- 表中包含的列数相对比较少;
- 表中的大多数查询都包含相对简单的where子句;
在创建索引时,需要认真选择表中的哪些列可以作为索引列。选择索引列有如下几个原则:
- 经常在where 子句中使用的列;
- 经常在表连接查询中用于表之间连接的列;
- 不宜将经常修改的列作为索引列;
- 不宜将经常在where子句中使用,但与函数或操作符相结合的列作为索引列;
- 对于取值较少的列,应考虑建立位图索引,而不应该采用B树索引;
如果对索引列使用了函数或操作符(如like),Oracle同样会对全表进行扫描;
2)索引列上所使用的操作符
对索引列的操作语句应该尽量避免“非”操作符的使用,例如not、!=、<>、!<、!>、not exists、not in和not like等,“非”操作符的使用会造成Oracle对表执行全表扫描。实际上,索引的作用是快速地告诉用户在表中有什么数据,而不能用来告诉用户在表中没有什么数据。
另外,使用like操作符可以应用通配符查询,但是如果用得不好,会产生性能上的问题,如like ‘%666%’不会被使用到索引,而like ‘666%’则会引用范围索引。因为第一个字符为通配符时,索引不再起作用,Oracle执行全表扫描。
3)避免对唯一索引列使用NULL值
使用unique关键字可以为列添加唯一索引,也就是说列的值不允许有重复值,但是,多个NULL值却可以同时存在,因为Oracle认为两个空值是不相等的。
向包含唯一索引的表中添加数据时,可以添加无数条NULL值的记录,但是由于这些记录都是空值,所以在索引中并不存在这些记录。因此,在where子句中使用is null或is not null,对唯一索引列进行空值比较时,Oracle将停止使用该列上的唯一索引,导致Oracle进行全表扫描。
列中包含NULL值的行都不会被包含在索引中,复合索引中只要有一列含有null值,那么这一列对于此 复合索引就是无效的。所以设计数据库时尽量不要让字段的默认值为NULL。
4)选择复合索引主列
创建复合索引时,应该按照如下原则:
- 选择经常在where子句中使用、并且由and操作符连接的列作为复合索引列;
- 选择where子句中使用频率相对较高的列排在最前面,或者根据需要为其他列创建单独的索引;
where子句中列的顺序与复合索引中列的顺序要保持一致,不然会影响查询效率。
只有当复合索引中的第一列被where子句使用时,Oracle才会使用该复合索引。
5)监视索引是否被使用
不必要的索引会对表的查询效率起副作用,所以应该经常检查索引是否被使用,这需要用到索引的监视功能。监视索引后,可以通过数据字典视图来了解索引的使用状态,如果确定索引不再需要使用,可以删除。
alter index index_name monitoring usage;
通过v$object_usage视图,查看索引的使用状态;