400 Star 1.3K Fork 1.5K

GVPopenGauss / openGauss-server

 / 详情

带有or过滤条件的连接查询没有进行下推,大数据量查询时影响性能

已验收
缺陷
创建于  
2022-11-30 15:17

【标题描述】:
【测试类型:SQL功能/存储功能/接口功能/工具功能/性能/并发/压力长稳/故障注入/安全/资料/编码规范】【测试版本:3.1.0】 问题描述
带有or过滤条件的连接查询没有进行下推,大数据量时影响性能。
【操作系统和硬件信息】(查询命令: cat /etc/system-release, uname -a):

【测试环境】(单机/1主x备x级联备):
单机
【被测功能】:

【测试类型】:

【数据库版本】(查询命令: gaussdb –V):

【预置条件】:
create table k1(id int,id1 int);
create table k2(id int,id1 int);
【操作步骤】(请填写详细的操作步骤):
explain select * from k1,k2 where (k1.id=1 and k2.id=2) or (k1.id=2 and k2.id=1);

【预期输出】:
pg12输出如下:

Nested Loop  (cost=0.00..94.44 rows=1 width=16)
   Join Filter: (((k1.id = 1) AND (k2.id = 2)) OR ((k1.id = 2) AND (k2.id = 1)))
   ->  Seq Scan on k1  (cost=0.00..42.23 rows=21 width=8)
         Filter: ((id = 1) OR (id = 2))
   ->  Materialize  (cost=0.00..42.34 rows=21 width=8)
         ->  Seq Scan on k2  (cost=0.00..42.23 rows=21 width=8)
               Filter: ((id = 2) OR (id = 1))

【实际输出】:

Nested Loop  (cost=0.00..103977.88 rows=231 width=16)
   Join Filter: (((k1.id = 1) AND (k2.id = 2)) OR ((k1.id = 2) AND (k2.id = 1)))
   ->  Seq Scan on k1  (cost=0.00..31.49 rows=2149 width=8)
   ->  Materialize  (cost=0.00..42.23 rows=2149 width=8)
         ->  Seq Scan on k2  (cost=0.00..31.49 rows=2149 width=8)

【原因分析】:
缺少extract_restriction_or_clauses优化

【日志信息】(请附上日志文件、截图、coredump信息):

【测试代码】:

评论 (9)

sunshine_22 创建了缺陷

Hey @sunshine_22, Welcome to openGauss Community.
All of the projects in openGauss Community are maintained by @opengauss-bot.
That means the developers can comment below every pull request or issue to trigger Bot Commands.
Please follow instructions at Here to find the details.

Hi @sunshine_22, please use the command /sig xxx to add a SIG label to this issue.
For example: /sig sqlengine or /sig storageengine or /sig om or /sig ai and so on.
You can find more SIG labels from Here.
If you have no idea about that, please contact with @xiangxinyong , @zhangxubo .

胡正超 修改了描述

您好,关于这个优化点,曾出现过一个问题,or的短路作用会失效,最终结果将代码回退了。
参考: https://e.gitee.com/opengaussorg/dashboard?issue=I38C7H

yansong_lee 负责人设置为pengjiong
yansong_lee 优先级设置为次要

是不是placeholder导致的,我现在的本地修改是:
if (root->placeholder_list == NIL)
extract_restriction_or_clauses(root);

不是placeholder导致的,例如对于条件 (A1 and B1) or (sqrt(a2)>1 and B2),
由于join条件、数据内容等因素,当or前面不满足时,能保证a2列的值大于0,即:若B1为false,则a2 > 0。而当下推的话,B1无法保证a2 > 0,导致sqrt(a2)报错,入参为负值。
详细用例和分析可参考上面贴的issue里的评论。
当然这个issue内场景确实比较特殊且略带一些诡异和不讲理,其实只要是下推,都可能无法保证条件之间的短路关系,造成类似情况,之前应该只关注单点问题了,最后就回退掉这个优化了。如您对这种OR下推确实有需求的话,可以填报一个SQL sig议题,一起讨论一下。

pengjiong 添加协作者pengjiong
pengjiong 负责人pengjiong 修改为胡正超
pengjiong 取消协作者pengjiong

这样的话,我还是本地加个GUC参数吧,如果遇到上面情况,把优化关掉,或者缺省关闭,需要时打开!

嗯嗯,加个GUC参数确实是最快速简单且有效的方法。
如果可以的话,也欢迎您将优化代码贡献到社区,之前那个问题的年代社区组织还没有很成熟的运作起来,现在可以在 SQL SIG 进行讨论,这个优化点能带来的收益其实还是蛮大的。

那这个如果没有问题的话,issue关掉了?

胡正超 添加协作者胡正超
胡正超 负责人胡正超 修改为Carl
Carl 任务状态待办的 修改为已确认
Carl 任务状态已确认 修改为修复中
Carl 任务状态修复中 修改为已完成
Carl 任务状态已完成 修改为测试中
Carl 任务状态测试中 修改为已验收

登录 后才可以发表评论

状态
负责人
项目
里程碑
Pull Requests
关联的 Pull Requests 被合并后可能会关闭此 issue
分支
开始日期   -   截止日期
-
置顶选项
优先级
预计工期 (小时)
参与者(4)
5622128 opengauss bot 1581905080
C++
1
https://gitee.com/opengauss/openGauss-server.git
git@gitee.com:opengauss/openGauss-server.git
opengauss
openGauss-server
openGauss-server

搜索帮助