The row source tree is the core of the execution plan. The tree shows the following information:
An ordering of the tables referenced by the statement
An access method for each table mentioned in the statement
A join method for tables affected by join operations in the statement
Data operations like filter, sort, or aggregation 注意查询计划, 例如:
For example, in the following explain plan, the last step is a very unselective range scan that is executed 76563 times,
accesses 11432983 rows, throws away 99% of them, and retains 76563 rows. Why access 11432983 rows to realize that only 76563 rows are needed?
Rows Execution Plan
-------- ----------------------------------------------------
12 SORT AGGREGATE
2 SORT GROUP BY
76563 NESTED LOOPS
76575 NESTED LOOPS
19 TABLE ACCESS FULL CN_PAYRUNS_ALL
76570 TABLE ACCESS BY INDEX ROWID CN_POSTING_DETAILS_ALL
76570 INDEX RANGE SCAN (object id 178321)
76563 TABLE ACCESS BY INDEX ROWID CN_PAYMENT_WORKSHEETS_ALL
11432983 INDEX RANGE SCAN (object id 186024) 用 explain 来评估, 评估完以后, 要实测一下, 看执行是否满足要求 如何使用 explain (我们一般不这么用, 直接用 set autotrace on 或者 通过工具提供的自动就能看到)
EXPLAIN PLAN FORSELECT last_name FROM employees; EXPLAIN PLAN
SET STATEMENT_ID = 'st1' FOR -- 指定你刚刚执行的statement id, 方便在plan table 中查找到你刚刚执行的statement
SELECT last_name FROM employees; 直接看 reading EX:
SELECT phone_number FROM employees
WHERE phone_number LIKE '650%';
---------------------------------------
| Id | Operation | Name |
---------------------------------------
| 0 | SELECT STATEMENT | |
| 1 | TABLE ACCESS FULL| EMPLOYEES |
---------------------------------------
This plan shows execution of a SELECT statement. The table employees is accessed using a full table scan.
Every row in the table employees is accessed, and the WHERE clause criteria is evaluated for every row.
The SELECT statement returns the rows meeting the WHERE clause criteria. Viewing Parallel Execution with EXPLAIN PLAN {先不考虑并行, 感觉用到不多} 并行计划与普通计划的不同, 基本上普通计划与并行计划是一样的, 但是也少部分地方不一样, 比如下边的多表连接
普通计划: 多表连接时, 肯定是以小表作为主表(drive table)
并行计划: 多表连接时, 要以大表最为驱动表(主表)
一般, 只有数据量非常巨大的情况, 才考虑使用并行查询. EX: CREATE TABLE emp2 AS SELECT * FROM employees;
ALTER TABLE emp2 PARALLEL 2; EXPLAIN PLAN FOR
SELECT SUM(salary) FROM emp2 GROUP BY department_id;
SELECT PLAN_TABLE_OUTPUT FROM TABLE(DBMS_XPLAN.DISPLAY()); -- 查看对应的执行计划 --------------------------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU) | TQ |IN-OUT| PQ Distrib |
--------------------------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 107 | 2782 | 3 (34) | | | |
| 1 | PX COORDINATOR | | | | | | | |
| 2 | PX SEND QC (RANDOM) | :TQ10001 | 107 | 2782 | 3 (34) | Q1,01 | P->S | QC (RAND) |
| 3 | HASH GROUP BY | | 107 | 2782 | 3 (34) | Q1,01 | PCWP | |
| 4 | PX RECEIVE | | 107 | 2782 | 3 (34) | Q1,01 | PCWP | |
| 5 | PX SEND HASH | :TQ10000 | 107 | 2782 | 3 (34) | Q1,00 | P->P | HASH |
| 6 | HASH GROUP BY | | 107 | 2782 | 3 (34) | Q1,00 | PCWP | |
| 7 | PX BLOCK ITERATOR | | 107 | 2782 | 2 (0) | Q1,00 | PCWP | |
| 8 | TABLE ACCESS FULL| EMP2 | 107 | 2782 | 2 (0) | Q1,00 | PCWP | |
--------------------------------------------------------------------------------------------------------
The table EMP2 is scanned in parallel by one set of slaves while the aggregation for the GROUP BY is done by the second set.
The PX BLOCK ITERATOR row source represents the splitting up of the table EMP2 into pieces so as to divide the scan workload
between the parallel scan slaves. The PX SEND and PX RECEIVE row sources represent the pipe that connects the two slave sets
as rows flow up from the parallel scan, get repartitioned through the HASH table queue, and then read by and aggregated on the top slave set.
The PX SEND QC row source represents the aggregated values being sent to the QC in random (RAND) order.
The PX COORDINATOR row source represents the QC or Query Coordinator which controls and schedules the parallel plan appearing below it in the plan tree. Viewing Bitmap Indexes with EXPLAIN PLAN {先不考虑并行, bitmap索引在OLTP中不考虑}
EX:
SELECT * FROM t
WHERE c1 = 2
AND c2 <> 6
OR c3 BETWEEN 10 AND 20; SELECT STATEMENT
TABLE ACCESS T BY INDEX ROWID
BITMAP CONVERSION TO ROWID
BITMAP OR
BITMAP MINUS
BITMAP MINUS
BITMAP INDEX C1_IND SINGLE VALUE
BITMAP INDEX C2_IND SINGLE VALUE
BITMAP INDEX C2_IND SINGLE VALUE
BITMAP MERGE
BITMAP INDEX C3_IND RANGE SCAN 12.9 Viewing Partitioned Objects with EXPLAIN PLAN
RANGE Partitioning
CREATE TABLE emp_range
PARTITION BY RANGE(hire_date)
(
PARTITION emp_p1 VALUES LESS THAN (TO_DATE('1-JAN-1992','DD-MON-YYYY')),
PARTITION emp_p2 VALUES LESS THAN (TO_DATE('1-JAN-1994','DD-MON-YYYY')),
PARTITION emp_p3 VALUES LESS THAN (TO_DATE('1-JAN-1996','DD-MON-YYYY')),
PARTITION emp_p4 VALUES LESS THAN (TO_DATE('1-JAN-1998','DD-MON-YYYY')),
PARTITION emp_p5 VALUES LESS THAN (TO_DATE('1-JAN-2001','DD-MON-YYYY'))
)
AS SELECT * FROM employees;
EX 1 :
EXPLAIN PLAN FOR
SELECT * FROM emp_range;
---------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost | Pstart| Pstop |
---------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 105 | 13965 | 2 | | |
| 1 | PARTITION RANGE ALL| | 105 | 13965 | 2 | 1 | 5 |
| 2 | TABLE ACCESS FULL | EMP_RANGE | 105 | 13965 | 2 | 1 | 5 |
---------------------------------------------------------------------------------
In this example, the partition iterator covers all partitions (option ALL), because a predicate
was not used for pruning. The PARTITION_START and PARTITION_STOP columns of the PLAN_TABLE show access to all partitions from 1 to 5.
EX 2 :
EXPLAIN PLAN FOR
SELECT * FROM emp_range
WHERE hire_date >= TO_DATE('1-JAN-1996','DD-MON-YYYY');
--------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost | Pstart| Pstop |
--------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 3 | 399 | 2 | | |
| 1 | PARTITION RANGE ITERATOR| | 3 | 399 | 2 | 4 | 5 |
|* 2 | TABLE ACCESS FULL | EMP_RANGE | 3 | 399 | 2 | 4 | 5 |
--------------------------------------------------------------------------------------
In the previous example, the partition row source iterates from partition 4 to 5 because the database prunes the other partitions using a predicate on hire_date
EX 3 :
EXPLAIN PLAN FOR
SELECT * FROM emp_range
WHERE hire_date < TO_DATE('1-JAN-1992','DD-MON-YYYY');
------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost | Pstart| Pstop |
------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 133 | 2 | | |
| 1 | PARTITION RANGE SINGLE| | 1 | 133 | 2 | 1 | 1 |
|* 2 | TABLE ACCESS FULL | EMP_RANGE | 1 | 133 | 2 | 1 | 1 |
------------------------------------------------------------------------------------
In the previous example, only partition 1 is accessed and known at compile time; thus, there is no need for a partition row source.
Hash Partitioning
Oracle Database displays the same information for hash partitioned objects, except the partition row source name is
PARTITION HASH instead of PARTITION RANGE. Also, with hash partitioning, pruning is only possible using equality or IN-list predicates.
还有一些其他类型的, 目前忽略,比如混合Partitioning PLAN_TABLE Columns
PLAN_TABLE 有哪些内容, 可以查看这, 这有详细文档
The row source tree is the core of the execution plan. The tree shows the following information:
An ordering of the tables referenced by the statement
An access method for each table mentioned in the statement
A join method for tables affected by join operations in the statement
Data operations like filter, sort, or aggregation 注意查询计划, 例如:
For example, in the following explain plan, the last step is a very unselective range scan that is executed 76563 times,
accesses 11432983 rows, throws away 99% of them, and retains 76563 rows. Why access 11432983 rows to realize that only 76563 rows are needed?
Rows Execution Plan
-------- ----------------------------------------------------
12 SORT AGGREGATE
2 SORT GROUP BY
76563 NESTED LOOPS
76575 NESTED LOOPS
19 TABLE ACCESS FULL CN_PAYRUNS_ALL
76570 TABLE ACCESS BY INDEX ROWID CN_POSTING_DETAILS_ALL
76570 INDEX RANGE SCAN (object id 178321)
76563 TABLE ACCESS BY INDEX ROWID CN_PAYMENT_WORKSHEETS_ALL
11432983 INDEX RANGE SCAN (object id 186024) 用 explain 来评估, 评估完以后, 要实测一下, 看执行是否满足要求 如何使用 explain (我们一般不这么用, 直接用 set autotrace on 或者 通过工具提供的自动就能看到)
EXPLAIN PLAN FORSELECT last_name FROM employees; EXPLAIN PLAN
SET STATEMENT_ID = 'st1' FOR -- 指定你刚刚执行的statement id, 方便在plan table 中查找到你刚刚执行的statement
SELECT last_name FROM employees; 直接看 reading EX:
SELECT phone_number FROM employees
WHERE phone_number LIKE '650%';
---------------------------------------
| Id | Operation | Name |
---------------------------------------
| 0 | SELECT STATEMENT | |
| 1 | TABLE ACCESS FULL| EMPLOYEES |
---------------------------------------
This plan shows execution of a SELECT statement. The table employees is accessed using a full table scan.
Every row in the table employees is accessed, and the WHERE clause criteria is evaluated for every row.
The SELECT statement returns the rows meeting the WHERE clause criteria. Viewing Parallel Execution with EXPLAIN PLAN {先不考虑并行, 感觉用到不多} 并行计划与普通计划的不同, 基本上普通计划与并行计划是一样的, 但是也少部分地方不一样, 比如下边的多表连接
普通计划: 多表连接时, 肯定是以小表作为主表(drive table)
并行计划: 多表连接时, 要以大表最为驱动表(主表)
一般, 只有数据量非常巨大的情况, 才考虑使用并行查询. EX: CREATE TABLE emp2 AS SELECT * FROM employees;
ALTER TABLE emp2 PARALLEL 2; EXPLAIN PLAN FOR
SELECT SUM(salary) FROM emp2 GROUP BY department_id;
SELECT PLAN_TABLE_OUTPUT FROM TABLE(DBMS_XPLAN.DISPLAY()); -- 查看对应的执行计划 --------------------------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU) | TQ |IN-OUT| PQ Distrib |
--------------------------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 107 | 2782 | 3 (34) | | | |
| 1 | PX COORDINATOR | | | | | | | |
| 2 | PX SEND QC (RANDOM) | :TQ10001 | 107 | 2782 | 3 (34) | Q1,01 | P->S | QC (RAND) |
| 3 | HASH GROUP BY | | 107 | 2782 | 3 (34) | Q1,01 | PCWP | |
| 4 | PX RECEIVE | | 107 | 2782 | 3 (34) | Q1,01 | PCWP | |
| 5 | PX SEND HASH | :TQ10000 | 107 | 2782 | 3 (34) | Q1,00 | P->P | HASH |
| 6 | HASH GROUP BY | | 107 | 2782 | 3 (34) | Q1,00 | PCWP | |
| 7 | PX BLOCK ITERATOR | | 107 | 2782 | 2 (0) | Q1,00 | PCWP | |
| 8 | TABLE ACCESS FULL| EMP2 | 107 | 2782 | 2 (0) | Q1,00 | PCWP | |
--------------------------------------------------------------------------------------------------------
The table EMP2 is scanned in parallel by one set of slaves while the aggregation for the GROUP BY is done by the second set.
The PX BLOCK ITERATOR row source represents the splitting up of the table EMP2 into pieces so as to divide the scan workload
between the parallel scan slaves. The PX SEND and PX RECEIVE row sources represent the pipe that connects the two slave sets
as rows flow up from the parallel scan, get repartitioned through the HASH table queue, and then read by and aggregated on the top slave set.
The PX SEND QC row source represents the aggregated values being sent to the QC in random (RAND) order.
The PX COORDINATOR row source represents the QC or Query Coordinator which controls and schedules the parallel plan appearing below it in the plan tree. Viewing Bitmap Indexes with EXPLAIN PLAN {先不考虑并行, bitmap索引在OLTP中不考虑}
EX:
SELECT * FROM t
WHERE c1 = 2
AND c2 <> 6
OR c3 BETWEEN 10 AND 20; SELECT STATEMENT
TABLE ACCESS T BY INDEX ROWID
BITMAP CONVERSION TO ROWID
BITMAP OR
BITMAP MINUS
BITMAP MINUS
BITMAP INDEX C1_IND SINGLE VALUE
BITMAP INDEX C2_IND SINGLE VALUE
BITMAP INDEX C2_IND SINGLE VALUE
BITMAP MERGE
BITMAP INDEX C3_IND RANGE SCAN 12.9 Viewing Partitioned Objects with EXPLAIN PLAN
RANGE Partitioning
CREATE TABLE emp_range
PARTITION BY RANGE(hire_date)
(
PARTITION emp_p1 VALUES LESS THAN (TO_DATE('1-JAN-1992','DD-MON-YYYY')),
PARTITION emp_p2 VALUES LESS THAN (TO_DATE('1-JAN-1994','DD-MON-YYYY')),
PARTITION emp_p3 VALUES LESS THAN (TO_DATE('1-JAN-1996','DD-MON-YYYY')),
PARTITION emp_p4 VALUES LESS THAN (TO_DATE('1-JAN-1998','DD-MON-YYYY')),
PARTITION emp_p5 VALUES LESS THAN (TO_DATE('1-JAN-2001','DD-MON-YYYY'))
)
AS SELECT * FROM employees;
EX 1 :
EXPLAIN PLAN FOR
SELECT * FROM emp_range;
---------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost | Pstart| Pstop |
---------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 105 | 13965 | 2 | | |
| 1 | PARTITION RANGE ALL| | 105 | 13965 | 2 | 1 | 5 |
| 2 | TABLE ACCESS FULL | EMP_RANGE | 105 | 13965 | 2 | 1 | 5 |
---------------------------------------------------------------------------------
In this example, the partition iterator covers all partitions (option ALL), because a predicate
was not used for pruning. The PARTITION_START and PARTITION_STOP columns of the PLAN_TABLE show access to all partitions from 1 to 5.
EX 2 :
EXPLAIN PLAN FOR
SELECT * FROM emp_range
WHERE hire_date >= TO_DATE('1-JAN-1996','DD-MON-YYYY');
--------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost | Pstart| Pstop |
--------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 3 | 399 | 2 | | |
| 1 | PARTITION RANGE ITERATOR| | 3 | 399 | 2 | 4 | 5 |
|* 2 | TABLE ACCESS FULL | EMP_RANGE | 3 | 399 | 2 | 4 | 5 |
--------------------------------------------------------------------------------------
In the previous example, the partition row source iterates from partition 4 to 5 because the database prunes the other partitions using a predicate on hire_date
EX 3 :
EXPLAIN PLAN FOR
SELECT * FROM emp_range
WHERE hire_date < TO_DATE('1-JAN-1992','DD-MON-YYYY');
------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost | Pstart| Pstop |
------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 133 | 2 | | |
| 1 | PARTITION RANGE SINGLE| | 1 | 133 | 2 | 1 | 1 |
|* 2 | TABLE ACCESS FULL | EMP_RANGE | 1 | 133 | 2 | 1 | 1 |
------------------------------------------------------------------------------------
In the previous example, only partition 1 is accessed and known at compile time; thus, there is no need for a partition row source.
Hash Partitioning
Oracle Database displays the same information for hash partitioned objects, except the partition row source name is
PARTITION HASH instead of PARTITION RANGE. Also, with hash partitioning, pruning is only possible using equality or IN-list predicates.
还有一些其他类型的, 目前忽略,比如混合Partitioning PLAN_TABLE Columns
PLAN_TABLE 有哪些内容, 可以查看这, 这有详细文档

12 Using_explain_plan的更多相关文章

  1. python 各模块

    01 关于本书 02 代码约定 03 关于例子 04 如何联系我们 1 核心模块 11 介绍 111 内建函数和异常 112 操作系统接口模块 113 类型支持模块 114 正则表达式 115 语言支 ...

  2. Python Standard Library

    Python Standard Library "We'd like to pretend that 'Fredrik' is a role, but even hundreds of vo ...

  3. 在mybatis中写sql语句的一些体会

    本文会使用一个案例,就mybatis的一些基础语法进行讲解.案例中使用到的数据库表和对象如下: article表:这个表存放的是文章的基础信息 -- ------------------------- ...

  4. AndroidStudio — Error:Failed to resolve: junit:junit:4.12错误解决

    原博客:http://blog.csdn.net/u013443865/article/details/50243193 最近使用AndroidStudio出现以下问题: 解决:打开app下的buil ...

  5. 读过MBA的CEO更自私?《哈佛商业评论》2016年第12期。4星

    老牌管理杂志.每期都值得精度.本期我还是给4星. 以下是本书中的一些内容的摘抄: 1:他们发现在Airbnb上,如果客人姓名听起来像黑人,那么比名字像白人的客人的接受率会低16%.#45 2:对立组织 ...

  6. 12个小技巧,让你高效使用Eclipse

    集成开发环境(IDE)让应用开发更加容易.它们强调语法,让你知道是否你存在编译错误,在众多的其他事情中允许你单步调试代码.像所有的IDE一 样,Eclipse也有快捷键和小工具,这些会让您感觉轻松许多 ...

  7. 第12章 Linux系统管理

    1. 进程管理 1.1 进程查看 (1)进程简介 进程是正在执行的一个程序或命令(如ls命令也是一个进程),每个进程都是一个运行的实体,都有自己的地址空间,并占用一定的系统资源. (2)进程管理的作用 ...

  8. Jexus Web Server 完全傻瓜化图文配置教程(基于Ubuntu 12.04.3 64位)[内含Hyper-v 2012虚拟机镜像下载地址]

    1. 前言 近日有感许多新朋友想尝试使用Jexus,不过绝大多数都困惑徘徊在Linux如何安装啊,如何编译Mono啊,如何配置Jexus啊...等等基础问题,于是昨日向宇内流云兄提议,不如搞几个配置好 ...

  9. CSharpGL(12)用T4模板生成CSSL及其renderer代码

    CSharpGL(12)用T4模板生成CSSL及其renderer代码 2016-08-13 由于CSharpGL一直在更新,现在这个教程已经不适用最新的代码了.CSharpGL源码中包含10多个独立 ...

随机推荐

  1. 使用 Bootstrap Typeahead 组件

    Bootstrap 中的 Typeahead 组件就是通常所说的自动完成 AutoComplete,功能很强大,但是,使用上并不太方便.这里我们将介绍一下这个组件的使用. 第一,简单使用 首先,最简单 ...

  2. UVA 12950 : Even Obsession(最短路Dijkstra)

    https://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem& ...

  3. 在ecshop顶部会员信息提示区显示会员等级

    会员登陆后,在顶部会员信息提示区显示会员等级会员登陆后会在顶部出现这样的提示:您好,test2, 欢迎您回来 ! 进入用户中心 |退出现在设想在会员名后面加上“会员等级”效果如下:您好,test2,  ...

  4. ACM题目————吝啬的国度

    描述 在一个吝啬的国度里有N个城市,这N个城市间只有N-1条路把这个N个城市连接起来.现在,Tom在第S号城市,他有张该国地图,他想知道如果自己要去参观第T号城市,必须经过的前一个城市是几号城市(假设 ...

  5. 手把手教你用C++ 写ACM自动刷题神器(冲入HDU首页)

    转载注明原地址:http://blog.csdn.net/nk_test/article/details/49497017 少年,作为苦练ACM,通宵刷题的你 是不是想着有一天能够荣登各大OJ榜首,俯 ...

  6. 棋盘问题 分类: 搜索 POJ 2015-08-09 13:02 4人阅读 评论(0) 收藏

    棋盘问题 Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 28474 Accepted: 14084 Description 在一 ...

  7. 测试-关于Unity获取子层级内容的几种接口(Transform FindChild, Component GetComponentInChildren,...)

    测试常用的层级内组件查找接口,但一些需求还是需要扩展 比如按照名称批量查找节点,查找接口对象等 1.Transform - Transform Find(string name) 可以直接根据名称搜索 ...

  8. C#实现中国天气网XML接口测试

    点击链接查看中国天气网接口说明,最近想研究一下接口测试,源于最近一次和某公司的技术总监(交大校友)谈话,发现接口测试的需求是比较大的,于是想要研究一下. 好不容易在网上找到了一个关于中国天气网的接口说 ...

  9. ssh 配置自动登录

    假定 机器A 连接至 机器B . 1. 在机器A上,生成RSA秘钥对 ssh-keygen -t rsa 期间passphrase不输入密码.默认生成文件至 ~/.ssh/ -rw------- we ...

  10. 2016年11月1日 星期二 --出埃及记 Exodus 19:17

    2016年11月1日 星期二 --出埃及记 Exodus 19:17 Then Moses led the people out of the camp to meet with God, and t ...