`
足至迹留
  • 浏览: 496895 次
  • 性别: Icon_minigender_1
  • 来自: OnePiece
社区版块
存档分类
最新评论

<让oracle跑得更快-4> 优化器(optimizer)

阅读更多
Oracle数据库中优化器(optimizer)是sql分析和执行的优化工具,它负责制定sql的执行计划,也就是它负责保证sql执行的效率最高,比如优化器决定oracle以什么样的方式访问数据,是全表扫描(Full Table Scan, FTS),索引范围扫描(Index Range Scan)还是全索引快速扫描(Index Fast Full Scan, INDEX_FFS);对于表关联查询,它负责确定表之间以一种什么方式来关联,比如hash_join还是nested loops或是merge join。这些因素直接决定着sql的执行效率,所以优化器是sql执行的核心,它做出的执行计划好坏,直接决定着sql的执行效率。
Oracle的优化器有两种,基于规则的优化器(RBO)和基于代价的优化器(CBO),从oracle10g开始,RBO已经被弃用(但是我们依然可以通过HINT方式来使用它)。

4.1 RBO基于规则的优化器
在8i之前,oracle使用的是一种叫做RBO(Rule Based Optimizer,基于规则的优化器)的优化器,它的执行机制非常简单,就是在优化器里嵌入若干种规则,执行的sql语句符合哪种规则,就按照规则制定出相应的执行计划,比如说表上有个索引,如果谓词上有索引的列存在,则oracle会选择索引,否则选择全表扫描;又比如,两个表关联的时候,按照表在sql中的位置来决定哪个是驱动表,哪个是被驱动表。
下图是RBO在选择执行计划的一个优先级列表。


事实是,走索引未必比走全表扫描快,还要看数据分布等。比如,首先创建一个分布极不均匀的表:
Create table t as select 1 id, object_name from dba_objects;
Update t set id=99 where rownum = 1; ---这样整个表就只有第一行的id=99;其余都是1.
Create index ind_t on t(id);
Select id, count(*) from t group by id;
结果:
ID   COUNT(*)
----------------------------
1	51080
99    1


在RBO的年代里,这两条的执行计划时这样的:
Select /*+ rule */ * from t where id=99;

执行计划


最后一句提示当前使用的优化器是RBO,建议使用CBO。

再次查询
Select /*+ rule*/ * from t where id=1;

执行计划:


使用hint /*+ rule*/的方式强制让oracle使用RBO优化器来产生执行计划,结果非常让人失望,oracle在id字段有索引的情况下,毫无悬念地全部选择了索引。
实际上我们知道,对于id=1,几乎所有的数据全都符合谓词条件,选择索引只能增加额外的开销(因为oracle要首先访问索引数据块,在索引上找到了相应的键值,然后按照键值上的rowid再去访问表中的相应数据),既然我们几乎要访问表中所有的数据,那么全表扫描自然是最优的选择,很遗憾的是,RBO让我们失望地做出了错误的选择。
RBO的情况就是这样,它是一种呆板、过时的优化器,已经在oracle10g以后的版本上被彻底剔除掉了(但仍然能通过使用hint来强制使用)。

4.2 CBO基于成本的优化器
从8i开始,oracle引入了CBO(Cost Based Optimizer, 基于成本的优化器),它的思路是让oracle获取所有执行计划相关的信息,通过对这些信息做计算分析,最后得出一个代价最小的执行计划作为最终执行计划。CBO是一种比RBO更理性的优化器。

还是拿上面的例子,看下CBO的表现:
Exec dbms_stats.gather_table_stats(user, ‘t’, cascade=>true);
Select /*+ all_rows */ * from t where id=1;

执行计划:


Select /*+ all_rows */ * from t where id=99;

执行计划:


CBO表现的非常完美,CBO会根据表的统计信息做出正确的执行计划:
Id=1, 全表扫描
Id=99, 索引扫描
因为这样的选择代价是最小的。从10g开始, oracle已经彻底丢弃了RBO即使在表、索引没有被分析的时候,oracle依然会使用CBO。此时,oracle会使用一种叫做动态采样的技术,在分析sql的时候,动态的收集表、索引上的一些数据块,使用这些数据块的信息及字典表中关于这些对象的信息来计算出执行计划的代价,进而挑选出最优的执行计划。
比如:
Create table t (x int, y varchar2(2000));
Insert into t select object_id, object_name from dba_objects;
Commit;
Create index t_ind on t(x);
Alter session set sql_trace=true;
Select count(x) from t where x <100;
Count(x)
------
98

Alter system flush shared_pool;
Set autotrace trace exp;
Set linesize 120;
Select * from t where x=100;



可以看到,当表没有做分析的时候,oracle会使用动态采样来收集统计信息,这个动作只有在sql执行的第一次,即硬分析阶段使用,后续的软分析将不再使用动态采样,直接使用第一次sql硬分析时生成的执行计划。

CBO优化器有两种可选的运行模式:
(1) FIRST_ROWS(n)
(2) ALL_ROWS

当设置优化器模式为FIRST_ROWS(n)时,意味着oracle在执行sql时,优先考虑将结果集中的前n条记录以最快的速度反馈回来,而其他的结果并不需要同时返回。这种需求在一些网站搜索或者BBS的分页上经常看到,比如每次只查询信息的前20条或BBS的前20个帖子,这时设置FIRST_ROW(n)就非常合适,优化器并不需要同时将所有符合条件的结果返回。比如:
Select /*+ first_rows(10) */ b.x, b.y
from (select /*+ first_rows(10) */ a.*, rownum rnum
from (select /*+ first_rows(10)*/ * from t order by x) a where rownum <= 20) b
where rnum >= 10;
这是一个典型的分页的例子,每次从结果取出10条记录。需要注意的是,排序使用的字段x必须创建有索引,否则CBO会忽略FIRST_ROWS(N)而使用ALL_ROWS.

ALL_ROWS在OLAP系统中使用得比较多,它的目的在于用最快的速度获得sql执行的最后一条记录,而不是前n条数据。和FIRST_ROWS(n)正好相反,ALL_ROWS强调sql整体的执行效率,而FIRST_ROWS(n)强调以最快的速度返回前n行,而不管所有的结果返回时长,可能最后一条要很长时间之后才能获得。
  • 大小: 118.6 KB
  • 大小: 147 KB
  • 大小: 132.4 KB
  • 大小: 137.3 KB
  • 大小: 202.8 KB
  • 大小: 169.2 KB
0
0
分享到:
评论

相关推荐

    让Oracle跑得更快.pdf-Oracle 10g 性能分析与优化思路

    《让Oracle跑得更快》是针对Oracle 10g数据库性能分析与优化的一份深入指南。Oracle数据库系统作为全球广泛使用的数据库管理系统之一,其性能优化对于企业数据处理效率至关重要。Oracle 10g版本在性能方面引入了许多...

    让Oracle跑得更快 Oracle 10g性能分析与优化思路.part2.rar

    第4章 优化器 66 4.1 rbo基于规则的优化器 66 4.2 cbo基于成本的优化器 69 第5章 执行计划 85 5.1 cardinality (基数) 85 5.2 sql的执行计划 94 第6章 hint 109 6.1 和优化器相关的hint 115 6.1.1 all_rows和first_...

    flink 1.6.0 源码包

    &lt;module&gt;flink-optimizer&lt;/module&gt; &lt;module&gt;flink-streaming-java&lt;/module&gt; &lt;module&gt;flink-streaming-scala&lt;/module&gt; &lt;module&gt;flink-connectors&lt;/module&gt; &lt;module&gt;flink-formats&lt;/module&gt; &lt;module&gt;flink-...

    让Oracle跑得更快 Oracle 10g性能分析与优化思路.part1.rar

    第4章 优化器 66 4.1 rbo基于规则的优化器 66 4.2 cbo基于成本的优化器 69 第5章 执行计划 85 5.1 cardinality (基数) 85 5.2 sql的执行计划 94 第6章 hint 109 6.1 和优化器相关的hint 115 6.1.1 all_rows和first_...

    Oracle的优化器(Optimizer)

    #### 一、Oracle优化器概述 在Oracle数据库中,每当执行SQL语句时,系统首先需要确定最佳的执行路径或计划,这一过程由**优化器(Optimizer)**负责。优化器的主要任务是评估SQL语句的不同执行计划,并从中选择一个最...

    Spring + Hibernate + Struts 事务配置小例子(带提示框等小技巧)

    &lt;prop key="hibernate.cglib.use_reflection_optimizer"&gt; true &lt;/prop&gt; &lt;prop key="hibernate.cache.provider_class"&gt; org.hibernate.cache.EhCacheProvider &lt;/prop&gt; &lt;prop key=...

    Laravel开发-laravel-image-optimizer

    在本文中,我们将深入探讨...理解并正确使用此扩展,能为你的 Laravel 应用带来显著的性能提升,为用户提供更快更流畅的浏览体验。在实际开发中,结合最佳实践和持续优化,可以进一步提升用户体验和网站的专业性。

    Ranger-Deep-Learning-Optimizer-master.zip

    该压缩包为Ranger 优化器(性能优于Adam)- a synergistic optimizer using RAdam (Rectified Adam) and LookAhead in one codebase。

    struts2的ssh手工配置全过程还带一个登陆例子的配置

    &lt;property name="dialect"&gt;org.hibernate.dialect.Oracle9Dialect&lt;/property&gt; &lt;property name="show_sql"&gt;false&lt;/property&gt; &lt;property name="format_sql"&gt;true&lt;/property&gt; &lt;property name="bytecode.use_...

    oracle-优化器详解.docx

    Oracle 优化器可以根据不同的优化目标生成不同的执行计划,例如,以最佳吞吐量为目标或以最快的响应速度为目标。 选择合适的优化器目标 -------------------- 默认情况下,CBO 以最佳吞吐量为目标,这意味着 ...

    SQL optimizer and rewriter. - SQL 优化器、重写器(辅助 SQL 调优)

    - SQL 优化器、重写器(辅助 SQL 调优)。SQL optimizer and rewriter. - SQL 优化器、重写器(辅助 SQL 调优)。SQL optimizer and rewriter. - SQL 优化器、重写器(辅助 SQL 调优)。SQL optimizer and rewriter. - ...

    win11系统优化器+win10系统优化器+Optimizer-14.5

    根据Windows版本的不同,优化器还允许您执行一些特定的调整。 支持 Windows10/11 软件特点:全语言支持(提供19种语言);提高系统和网络性能;禁用不必要的窗口服务;禁用 Windows 遥测、小娜等;禁用办公室遥测...

    mg-maven-resource-optimizer:简单的Maven插件,用于在构建时gzip JS和CSS文件

    mg-maven-资源优化器 简单的Maven插件,可在构建时将gzip JS和CSS文件压缩。 除了Maven本身,没有其他依赖项。 Maven依赖 Maven软件包发布在Github上: : 用法: &lt;plugin&gt; &lt;groupId&gt;com.manikanta&lt;/groupId&gt; ...

    android自动打包方法(ant+proguard+签名)知识.pdf

    &lt;zipalign file="${out.release.unaligned.dir}/${main.class}-${target}.apk" alignedfile="${out.release.dir}/${main.class}-${target}.apk" alignment="4" verbose="true"/&gt; &lt;!-- 签名APK --&gt; &lt;signing ...

    SQL Optimizer for Oracle - Basic.ppt

    《SQL Optimizer for Oracle - Basic》的培训课程主要讲解了如何高效优化Oracle数据库中的SQL语句,提升系统性能。课程涵盖了四个核心步骤、两种执行模式以及开发和优化流程。 首先,四个核心步骤是识别、优化、...

    Oracle练习-有答案<全套>

    通过学习SQL优化器的工作原理,如CBO(Cost-Based Optimizer)和RBO(Rule-Based Optimizer),你可以找出性能瓶颈并改进查询。索引的创建和管理,包括B树、位图和反向索引,也是提高查询速度的关键。 最后,Oracle...

    Fribbels-Epic-7-Optimizer:手机游戏Epic 7的齿轮优化器

    Fribbels Epic 7齿轮优化器 这是用于为Epic 7组织齿轮并优化齿轮和单元构建的工具。齿轮装置非常耗时,而且在游戏中很难找到最佳齿轮组合,因此我这样做是为了帮助简化齿轮安装过程。 快来加入Fribbels E7 ...

Global site tag (gtag.js) - Google Analytics