将 SQL 语句更改为 EXISTS 子句

Posted

技术标签:

【中文标题】将 SQL 语句更改为 EXISTS 子句【英文标题】:Change SQL statement to EXISTS clause 【发布时间】:2019-12-11 08:59:40 【问题描述】:

给定以下 SQL 语句:

select 
    OBJECT_ID
FROM HPSFWY.RVERSIONING_1703 A 
WHERE A.STAMP_ID >1 
    AND A.OBJECT_REV NOT IN (
select MAX(OBJECT_REV)
from HPSFWY.RVERSIONING_1709763 B 
where B.COMMITID <= 6066 
    and B.OBJECT_ID = A.OBJECT_ID 
    ) 

在此查询中,where 子句 AND OBJECT_REV NOT IN 必须从 NOT IN 更改为等效的 EXISTS 语句。

我们试试这个

select 
OBJECT_ID
FROM HPSFWY.RVERSIONING_1703 A 
WHERE A.STAMP_ID >1 
AND exists (
select * 
from HPSFWY.RVERSIONING_1709763 B 
where B.COMMITID <= 6066 
and B.OBJECT_ID = A.OBJECT_ID 
and B.OBJECT_REV > A.OBJECT_REV) ;

它给了我们接近的结果,但不一样

【问题讨论】:

请展示您的尝试:试错是一种比简单地要求别人为您完成工作更好的学习方式。 用它们所属的表别名来限定列名。 相当于NOT IN 将是NOT EXISTS 重写它以使用EXISTS 将是一个完全不同的查询 不是您问题的答案,但A.OBJECT_REV NOT IN (SELECT MAX(... 似乎很奇怪,因为后者返回一条记录。你可以考虑A.OBJECT_REV &lt;&gt; (SELECT MAX(... 【参考方案1】:

你可以像这样使用NOT EXISTS

SELECT A.OBJECT_ID
FROM HPSFWY.RVERSIONING_1703 A 
WHERE 
  A.STAMP_ID > 1 
  AND 
  NOT EXISTS (
    SELECT 1 FROM (
      SELECT MAX(B.OBJECT_REV) MAXOBJECT_REV
      FROM HPSFWY.RVERSIONING_1709763 B 
      WHERE B.COMMITID <= 6066 AND B.OBJECT_ID = A.OBJECT_ID 
    ) t
    WHERE t.MAXOBJECT_REV = A.OBJECT_REV
  )

注意:NOT IN 的子查询:

select MAX(OBJECT_REV)
from HPSFWY.RVERSIONING_1709763 B 
where B.COMMITID <= 6066 and B.OBJECT_ID = A.OBJECT_ID 

仅返回 1 行 1 列。 因此,您可以像这样使用&lt;&gt; 而不是NOT IN

SELECT A.OBJECT_ID
FROM HPSFWY.RVERSIONING_1703 A 
WHERE 
  A.STAMP_ID > 1 
  AND 
  A.OBJECT_REV <> (
    SELECT MAX(OBJECT_REV)
    FROM HPSFWY.RVERSIONING_1709763 B 
    WHERE B.COMMITID <= 6066 AND B.OBJECT_ID = A.OBJECT_ID 
  ) 

【讨论】:

谢谢,但是我们在 DB2 上遇到错误:“A.OBJECT_ID”是一个未定义的名称.. SQLCODE=-204, SQLSTATE=42704, DRIVER=3.69.56 B.OBJECT_ID = 看起来像错误A.OBJECT_ID B.OBJECT_ID = A.OBJECT_ID 是您代码的一部分。您的第一个查询有效吗? 是的,第一个查询有效。您的查询适用于 Microsoft SQL,但不适用于 DB2。原始查询适用于双方服务器 查询在 DB2 中的语法也很好,请检查:dbfiddle.uk/… 是的,您的查询通过了 db2 检查语法,但是当我们尝试运行时它失败了: SELECT A.OBJECT_ID FROM HPSFWY.RVERSIONING_1703 A WHERE A.STAMP_ID > 1 AND NOT EXISTS ( SELECT 1 FROM ( SELECT MAX (B.OBJECT_REV) MAXOBJECT_REV FROM HPSFWY.RVERSIONING_1709763 B WHERE B.COMMITID

以上是关于将 SQL 语句更改为 EXISTS 子句的主要内容,如果未能解决你的问题,请参考以下文章

MySQL的子查询中FROM和EXISTS子句的使用教程

SQL语句优化

SQL Group By and Have 子句和 exists 子句

即使插入了列,“WHERE”子句中的 SQL 未知列

如何使用 sql server exists 子句进行优化?

SQL语句中,子句不能使用列别名问题