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)

我不知道最后一句话在哪里起作用?

您的查询是:

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. 您将从客户和订单中获得所有符合基于客户密钥字段的条件的记录
  2. 谓词信息将输出限定为o_totalprice(顺便说一句,为了便于阅读,应该澄清这个字段来自哪里,尽管我猜是来自订单表(不是从子查询中检索到的数据集的一部分
  3. 子查询使用orders.ocustkey>=获取匹配零件和订单之间连接的所有零售价格值0和0.1*o_totalprice>=0

考虑到这一点,国会预算办公室是:

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

这只是您的执行计划的概述,以及国会预算办公室使用这些访问路径的原因。

最新更新