问题描述
我有两个复杂的,昂贵的查询,我已经执行了一个联合,所有这些查询都汇集在一起,以便在报告工具中使用
我有一个绑定变量,如果设置为一个值,则联合查询应执行联合的第一部分。如果将bind变量设置为第二个值,则应执行union查询的第二部分。
但是,当我查看跟踪和/或解释我的查询的计划时,存在来自联合查询的两个部分的成本。
这是我正在尝试做的简化版本:
然后我的查询是:
我希望,如果我为P_Type提供绑定值 '1',那么CBO/查询实际上只会访问表t1 (表t2的基数/成本为零)。
但是,我看到的是来自两个表的成本和基数,无论我分配给bind变量的值如何
如何强制CBO/数据库 “修剪” 查询的那些部分,其中条件/绑定值指示联合查询的一部分是不相关的?
我不想把它分成两个不同的查询,因为报告上有很多格式,我需要为这两个查询复制。
非常感谢您的反馈...
Oracle数据库企业版12.1.0.2,带SQL调优选项
我有一个绑定变量,如果设置为一个值,则联合查询应执行联合的第一部分。如果将bind变量设置为第二个值,则应执行union查询的第二部分。
但是,当我查看跟踪和/或解释我的查询的计划时,存在来自联合查询的两个部分的成本。
这是我正在尝试做的简化版本:
create table t1 as select 'T1' as ttype, 'Gadget 1' as descr from dual union all select 'T2' as ttype, 'Gadget 2' as descr from dual union all select 'T3' as ttype, 'Gadget 3' as descr from dual; create table t2 as select 'T21' as ttype, 'Widget 1' as descr from dual union all select 'T22' as ttype, 'Widget 2' as descr from dual union all select 'T23' as ttype, 'Widget 3' as descr from dual; 3' as ttype, 'Widget 3' as descr from dual;复制
然后我的查询是:
select ttype, descr from t1 where :P_Type='1' union all select ttype, descr from t2 where :P_Type='2';复制
我希望,如果我为P_Type提供绑定值 '1',那么CBO/查询实际上只会访问表t1 (表t2的基数/成本为零)。
但是,我看到的是来自两个表的成本和基数,无论我分配给bind变量的值如何
如何强制CBO/数据库 “修剪” 查询的那些部分,其中条件/绑定值指示联合查询的一部分是不相关的?
我不想把它分成两个不同的查询,因为报告上有很多格式,我需要为这两个查询复制。
非常感谢您的反馈...
Oracle数据库企业版12.1.0.2,带SQL调优选项
专家解答
你在看estimated中的行explain计划,或者actual中的行execution计划?
请记住,解释计划成本和基数是估计。这些是在不知道绑定值是什么的情况下生成的。
Bind变量peeking允许优化器根据输入调整计划。但在这种情况下没关系。无论您分配给什么值,计划都是相同的: P_Type。
例如,在下面的执行计划中,请注意开始和A行对于t2都是零。
步骤2和4中的滤波器操作短路处理。如果条件为true,则数据库仅在其下方进行完整扫描:
所以它已经修剪了查询的执行!
记住: 要评估一个计划,你必须看看它所做的实际工作。
请记住,解释计划成本和基数是估计。这些是在不知道绑定值是什么的情况下生成的。
Bind变量peeking允许优化器根据输入调整计划。但在这种情况下没关系。无论您分配给什么值,计划都是相同的: P_Type。
例如,在下面的执行计划中,请注意开始和A行对于t2都是零。
步骤2和4中的滤波器操作短路处理。如果条件为true,则数据库仅在其下方进行完整扫描:
create table t1 as select 'T1' as ttype, 'Gadget 1' as descr from dual union all select 'T2' as ttype, 'Gadget 2' as descr from dual union all select 'T3' as ttype, 'Gadget 3' as descr from dual; create table t2 as select 'T21' as ttype, 'Widget 1' as descr from dual union all select 'T22' as ttype, 'Widget 2' as descr from dual union all select 'T23' as ttype, 'Widget 3' as descr from dual; set serveroutput off var p_type varchar2(1); exec :p_type := '1'; select /*+ gather_plan_statistics */ttype, descr from t1 where :P_Type='1' union all select ttype, descr from t2 where :P_Type='2'; select * from table(dbms_xplan.display_cursor(null, null, 'ROWSTATS LAST +COST')); ---------------------------------------------------------------------------- | Id | Operation | Name | Starts | E-Rows | Cost (%CPU)| A-Rows | ---------------------------------------------------------------------------- | 0 | SELECT STATEMENT | | 1 | | 4 (100)| 3 | | 1 | UNION-ALL | | 1 | | | 3 | |* 2 | FILTER | | 1 | | | 3 | | 3 | TABLE ACCESS FULL| T1 | 1 | 3 | 2 (0)| 3 | |* 4 | FILTER | | 1 | | | 0 | | 5 | TABLE ACCESS FULL| T2 | 0 | 3 | 2 (0)| 0 | ---------------------------------------------------------------------------- Predicate Information (identified by operation id): --------------------------------------------------- 2 - filter(:P_TYPE='1') 4 - filter(:P_TYPE='2')复制
所以它已经修剪了查询的执行!
记住: 要评估一个计划,你必须看看它所做的实际工作。
「喜欢这篇文章,您的关注和赞赏是给作者最好的鼓励」
关注作者
【版权声明】本文为墨天轮用户原创内容,转载时必须标注文章的来源(墨天轮),文章链接,文章作者等基本信息,否则作者和墨天轮有权追究责任。如果您发现墨天轮中有涉嫌抄袭或者侵权的内容,欢迎发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。
评论
相关阅读
Oracle RAC 一键安装翻车?手把手教你如何排错!
Lucifer三思而后行
596次阅读
2025-04-15 17:24:06
【纯干货】Oracle 19C RU 19.27 发布,如何快速升级和安装?
Lucifer三思而后行
567次阅读
2025-04-18 14:18:38
XTTS跨版本迁移升级方案(11g to 19c RAC for Linux)
zwtian
485次阅读
2025-04-08 09:12:48
Oracle数据库一键巡检并生成HTML结果,免费脚本速来下载!
陈举超
473次阅读
2025-04-20 10:07:02
【ORACLE】记录一些ORACLE的merge into语句的BUG
DarkAthena
457次阅读
2025-04-22 00:20:37
【ORACLE】你以为的真的是你以为的么?--ORA-38104: Columns referenced in the ON Clause cannot be updated
DarkAthena
432次阅读
2025-04-22 00:13:51
Oracle 19c RAC更换IP实战,运维必看!
szrsu
432次阅读
2025-04-08 23:57:08
【活动】分享你的压箱底干货文档,三篇解锁进阶奖励!
墨天轮编辑部
417次阅读
2025-04-17 17:02:24
火焰图--分析复杂SQL执行计划的利器
听见风的声音
362次阅读
2025-04-17 09:30:30
3月“墨力原创作者计划”获奖名单公布
墨天轮编辑部
358次阅读
2025-04-15 14:48:05