首页 > 解决方案 > Oracle 执行计划中的 TABLE ACCESS FULL

问题描述

我的任务是找出解释计划的 SELECT 语句

------------------------------------------
| Id | Operation              | Name     |
------------------------------------------
| 0  | SELECT STATEMENT       |          |
| 1  |  HASH JOIN RIGHT ANTI  |          |
| 2  |   VIEW                 | VW_NSO_1 |
| 3  |    HASH JOIN RIGHT SEMI|          | 
| 4  |     TABLE ACCESS FULL  | PART     |
| 5  |     TABLE ACCESS FULL  | ORDERS   |
| 6  |   TABLE ACCESS FULL    | CUSTOMER |
------------------------------------------

我能够从 ID 0-5 中找到 select 语句,但第 6 行是什么意思?到目前为止,这是我设法弄清楚的,我无法理解最后一句话的作用。

select *
from customer c join orders o
on c.custkey = o.custkey
where o_totalprice
not in 
(select p_retailprice
from part p join orders o
on orders.o_custkey >= 0 and 0.1*o_totalprice >= 0)

我无法理解最后一句话的作用?

标签: oraclesql-execution-plan

解决方案


您的查询是:

select *
from customer c join orders o
on c.custkey = o.custkey
where o_totalprice
not in 
(select p_retailprice
from part p join orders o
on orders.o_custkey >= 0 and 0.1*o_totalprice >= 0)

你的解释计划是

------------------------------------------
| Id | Operation              | Name     |
------------------------------------------
| 0  | SELECT STATEMENT       |          |
| 1  |  HASH JOIN RIGHT ANTI  |          |
| 2  |   VIEW                 | VW_NSO_1 |
| 3  |    HASH JOIN RIGHT SEMI|          | 
| 4  |     TABLE ACCESS FULL  | PART     |
| 5  |     TABLE ACCESS FULL  | ORDERS   |
| 6  |   TABLE ACCESS FULL    | CUSTOMER |
------------------------------------------

在您的情况下,会发生以下情况:

  1. 您将从客户和订单中获取与基于 custkey 字段的条件匹配的所有记录。
  2. 您的谓词信息将输出分隔为那些 o_totalprice (顺便说一下,它应该澄清以方便阅读该字段的来源,尽管我猜是来自订单表)不是从子查询中检索到的数据集的一部分。
  3. 子查询使用orders.o_custkey >= 0 和0.1*o_totalprice >= 0 获取与part 和orders 之间的连接相匹配的p_retailprice 的所有值

考虑到这一点,CBO 是:

  • 通过 TABLE FULL SCAN 访问(第 6 行)表 CUSTOMER,这是合乎逻辑的,因为您正在从表中获取所有字段,并且您可能没有超过 custkey 的索引。
  • 在 PARTS 和 ORDERS 之间进行 HASH SEMI JOIN(第 3 行)。一般情况下,半连接用于in 或exists 子句,只要满足exists 条件或in 条件,连接就会停止。
  • 第 1 行的 HASH JOIN ANTI 是优化器将连接谓词推送到视图中时,通常是在反连接(不在)到位时。然后将其连接到第 6 行的 CUSTOMER TABLE。
  • 您仅在连接的右表( ORDERS )中进行过滤,这就是访问反映这一点的原因。

这只是您的执行计划的概述以及 CBO 使用这些访问路径的原因。


推荐阅读