《通过索引提升SQL性能案例一则》提到的案例,处理不太准确,有必要纠正下,更要谢谢老虎刘老师的耐心指正。
原始SQL,跑出的执行计划,是INDEX SKIP SCAN,确实是低效的,
select t.AGENT as agent,
nvl(sum(case
when t.operation_type = 'A' then 1 else 0 end),0) as
DflCount,
nvl(sum(case
when t.operation_type = 'B' then 1 else 0 end),0) as
IfCount,
nvl(sum(case
when t.operation_type = 'C' then 1 else 0 end),0) as
AecCount,
nvl(sum(case
when t.operation_type = 'D' then 1 else 0 end),0) as
BsCount
from OP_LOG t
where
t.code = 'AA'
and t.ORI_CODE = 'ABC'
and t.T_DATE BETWEEN to_date('20201209','yyyymmdd') and to_date('20201209','yyyymmdd')
and IS_VALID = 1
and t.operation_type in ('A','B','C','D')
group by t.agent
order by agent;
误区1,agent加到复合索引
因为原打算利用索引有序的特性,将agent加到索引中,利用复合索引(t_code, ori_code, t_date, t_no, agent),避免排序,但实际上,SQL中索引列条件t_date不是等值查询,而是范围查询,对这个复合索引来说,agent还可能是无序的。因此如果遵从“等值条件在前,范围条件在后”的索引构建原则,复合索引不应该加上agent,而可以考虑将operation_type加到索引中,并且放到t_date前。至于is_valid,number类型,长度定义为1,当前值都是1,放到索引access这个值,还是回表filter,我倒是觉得区别不会很大。
误区2,未考虑直方图
表中数据未必都是均匀分布的,尤其像operation_type的值,可能存在差异,因此还是需要看下检索字段的数据分布情况,如果存在倾斜,采集直方图,会对不同的值选择正确的执行计划有所帮助。
从这个案例来看,构建不同的索引,我们得到的优化程度是不同的,但是归根结底,还是需要踏实下来好好了解索引等这些知识的基本原理,结合实际问题,不断纠正自己错误的观念,对我来说,这条路上还是有很多积累和提升的地方。
服务器托管,北京服务器托管,服务器租用 http://www.fwqtg.net
机房租用,北京机房租用,IDC机房托管, http://www.fwqtg.net
相关推荐: Python潮流周刊#4:Python 2023 语言峰会
你好,我是猫哥。这里记录每周值得分享的 Python 及通用技术内容,本期是特别加更版,聚焦于 Python 官方 2023 年语言峰会的系列博客。 博客原文:https://pythoncat.top/posts/2023-05-31-weekly4 每年在…