oracle优化器缺陷(二)

今天看了一下好友anbob的文章,主要内容涉及CBO的一些查询转换,主题是在开发场景中如查询分页计算多少页或统计查询,有些开发是习惯基于明细的查询SQL,而外层直接加1层汇聚查询,如select count(*) from (select ….), 但子查询中可能有一些函数或主查询根本不需要的列, 在oracle中的查询转换中如select-project-join或select list pruning, 或VIEW merge SPJ,CVM 都是为了不影响SQL结果一致性,而优化低效的SQL。

Oracle、Oceanbase、Kingbase、GaussDB、达梦数据库比较系列(二十七):子查询中的函数投影裁剪

文章讲述的内容是在内嵌视图中的函数,在做了merge view转换之后,不需要的字段会被裁剪掉(SLP)。

但是在我自己测试的时候觉得还是存在一些小缺陷。记录一下。先说结论,我个人认为SLP投影应该发生在merge view之前。

测试demo:

SPJ的simple view,我就不测试了,主要测试一个带有group by的complex view。

由于data_object_id为普通索引,oracle的索引是不存储null的,所以特意加了条件is not null。可以发现view merge并没有发生,所以就不涉及后续的SLP了。假如SLP是在VIEW MERGE之前,该sql完全可以不需要访问表T,访问DATA_OBJECT_ID上的索引即可。

拒绝view merge的理由是包含了聚合并且外部查询不包含其他表:

将group by字段换成主键时,又可以了。

一开始进行view merge评估时同样也是判断cvm无法合并

但由于object_id为主键,这个时候做了一个group by消除,把group by去掉了

之后对于SPJ简单视图做了,view merge

再经过SLP转换为最终sql:

这只是碰巧碰到了主键的优势,能够对该聚合做group by消除。

假如SLP投影发生在merge view之前:

是否就能改写为:

执行计划也将变为:

 

 

此条目发表在Oracle, Oralce performance分类目录,贴了, , 标签。将固定链接加入收藏夹。

发表回复

您的电子邮箱地址不会被公开。 必填项已用*标注