9i前的RBO不熟,也就不敢妄言。
关于10g后的CBO,谈下我的理解。
首先,影响优化器执行计划最主要的因素是统计信息。优化器根据统计信息情况,单表上选择全表扫描还是索引。表联接方式上选择嵌套,哈希还是合并排序。不同的统计信息将会生成不同的执行计划。很多时候发现之前跑的好好的sql,突然变慢了,多数情况下重新收集下统计信息便解决了。统计信息这一块需要关注直方图这一块,很多生产环境都存在数据倾斜的情况,如若未准确收集直方图,那么生成的执行计划便有失偏颇。
--------------------------------------------------------------------------------------------------------------------
第二点,sql语句的写法问题。比如字段上有索引,但谓词条件写成like '%xxx%'方式,将导致该字段上索引不可用。比如表连接方式用<>之类,将无法使用hash join。其实这些与其说是写法问题,倒不如说是oracle自身有一定的编码规则,符合该规则条件,方可用到index之类。
--------------------------------------------------------------------------------------------------------------------
第三点,也是最无奈的一点,CBO的自身缺陷问题。很多时候,统计信息是最新的,也符合写法规范,但CBO就是不生成我们所期待的执行计划。这个时候,通常要改变sql语句的逻辑写法,比如标量子查询可否换成左连接,用with as替换一些子查询等,以期待oracle生成更高效率的执行计划。另外,就是使用hint来迫使CBO生成你所期待的执行计划,但CBO不一定就范。
谈及缺陷,也不算不上缺陷,尤其是表越多,将会出现更多排列的可能性,oracle不可能将所有执行计划都生成出来然后选择一个最优的,定是按照一定比例择取,但具体多少,我不详。也就是说,DBA完全可以凭借自身对你所管理的oracle了解程度,给sql语句指定一个最优的执行计划。
--------------------------------------------------------------------------------------------------------------------
其他还有一些细节问题,可在日常工作中慢慢体会,cbo还是相当强大的。