You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在PostgreSQL中更高效地编写多个EXISTS子查询

优化多子查询的工作流关联查询

我需要查询同时关联了两种特定任务类型的工作流,现有查询能得到正确结果,但用了多个EXISTS子查询,想改成更高效的单查询或用连接实现。

原查询代码:

SELECT *
FROM   workflow w
WHERE  EXISTS (SELECT ti.id
               FROM   task_instance ti
                      left join workflow_task_instance wti
                             ON ti.id = wti.task_instance_id
               WHERE  ti.task_type = 'TASK_ONE'
                      AND wti.workflow_id = w.id)
       AND EXISTS (SELECT ti.id
                   FROM   task_instance ti
                          left join workflow_task_instance wti
                                 ON ti.id = wti.task_instance_id
                   WHERE  ti.task_type = 'TASK_TWO'
                          AND wti.workflow_id = w.id); 

方案一:JOIN+GROUP BY+HAVING(单查询实现)

通过关联表筛选目标任务,按工作流分组后校验是否同时包含两种任务类型:

SELECT w.*
FROM workflow w
JOIN workflow_task_instance wti ON w.id = wti.workflow_id
JOIN task_instance ti ON wti.task_instance_id = ti.id
WHERE ti.task_type IN ('TASK_ONE', 'TASK_TWO')
GROUP BY w.id, w.[其他工作流表字段] -- 需根据数据库规则,将SELECT中的非聚合字段加入GROUP BY
HAVING COUNT(DISTINCT ti.task_type) = 2;

注:COUNT(DISTINCT)用于避免同一任务类型重复计数导致的误判,如果单个工作流不会关联多个同类型任务,也可以简化为COUNT(*) = 2,但前者兼容性和严谨性更强。

方案二:IN子查询(单嵌套子查询)

先在子查询中筛选出符合条件的工作流ID,再关联主表获取详情:

SELECT *
FROM workflow w
WHERE w.id IN (
    SELECT wti.workflow_id
    FROM workflow_task_instance wti
    JOIN task_instance ti ON wti.task_instance_id = ti.id
    WHERE ti.task_type IN ('TASK_ONE', 'TASK_TWO')
    GROUP BY wti.workflow_id
    HAVING COUNT(DISTINCT ti.task_type) = 2
);

注:这种方式将筛选逻辑集中在子查询,主表只需匹配已过滤的ID,减少主查询的计算量。

方案三:多JOIN替代EXISTS(无嵌套子查询)

通过两次关联分别匹配两种任务类型,最后去重得到结果:

SELECT DISTINCT w.*
FROM workflow w
JOIN workflow_task_instance wti1 ON w.id = wti1.workflow_id
JOIN task_instance ti1 ON wti1.task_instance_id = ti1.id AND ti1.task_type = 'TASK_ONE'
JOIN workflow_task_instance wti2 ON w.id = wti2.workflow_id
JOIN task_instance ti2 ON wti2.task_instance_id = ti2.id AND ti2.task_type = 'TASK_TWO';

注:DISTINCT用于去除因同一工作流关联多个同类型任务产生的重复行。

内容的提问来源于stack exchange,提问作者Nelaina

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.10 20:05:20