【问题标题】:How to find unmatched records in a single table?如何在单个表中查找不匹配的记录?
【发布时间】:2017-06-23 04:44:53
【问题描述】:

我正在为要插入到将用于多个挖掘任务的表中的事务记录抓取日志文件。每条记录(除其他事项外)都有一个 ID 和一个事务类型,请求或响应。请求/响应对将具有相同的 ID。

我的任务之一是找到所有没有相应响应的请求。我考虑过将表连接到自身,其中 A.ID = B.ID AND A.type = 'req' 和 B.type = 'res',但这与我需要的相反。

由于 ID 总是会出现一次或两次,是否有一个查询会选择 ID,而该 ID 在表中只出现一次?

【问题讨论】:

  • SELECT * FROM the_table A WHERE NOT EXISTS(SELECT * FROM the_table B where A.ID = B.ID AND A.type = 'req' and B.type = 'res');

标签: sql informix


【解决方案1】:

这是一种非常常见的查询类型。您可以尝试使用GROUP BY 聚合表中的ID 值,然后保留那些仅出现一次的ID

SELECT ID
FROM yourTable
GROUP BY ID
HAVING COUNT(*) = 1

如果您还想返回仅出现一次的 ID 的全部记录,您可以试试这个:

SELECT t1.*
FROM yourTable t1
INNER JOIN
(
    SELECT ID FROM yourTable GROUP BY ID HAVING COUNT(*) = 1
) t2
    ON t1.ID = t2.ID

【讨论】:

    【解决方案2】:

    直接的方式是NOT IN:

    select *
    from mytable
    where type = 'req'
    and id not in (select id from mytable where type = 'res');
    

    您可以使用NOT EXISTS 编写大致相同的内容,但查询的可读性会稍微降低:

    select *
    from mytable req
    where type = 'req'
    and not exists (select * from mytable res where type = 'res' and res.id = req.id);
    

    还有你可以使用的聚合形式,例如:

    select *
    from mytable
    where type = 'req'
    and id in 
    (
      select id 
      from mytable 
      group by id 
      having count(case when type = 'res' then 1 end) = 0
    );
    

    【讨论】:

      【解决方案3】:

      这会给你那些有请求但没有响应的人

      SELECT *
      FROM your_table A LEFT OUTER JOIN
      your_table B ON A.ID = B.ID 
      AND A.type = 'req' and B.type = 'res'
      WHERE B.ID IS NULL
      

      【讨论】:

      • 现在我展示了我对 SQL 的无知 - 如果加入 A.ID = B.ID,那么 B.ID 怎么可能是 NULL 而 A.ID 不是 NULL?
      • 这是 LEFT JOIN,您将在连接级别上匹配 A.ID = B.ID,因此如果有记录,则 WHERE 语句将为 false,并且不会选择该记录,因为它实际上有类型 = 请求。但如果它没有 type=req 则不会选择表 B 中的任何记录,这意味着 B.ID 为空
      • @Jim:这称为反连接。它主要用于在直接方法(即NOT EXISTSNOT IN)存在问题的弱DBMS中。
      猜你喜欢
      • 2012-01-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-01-19
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多