如何在左联接表中执行自联接?

时间:2019-11-11 05:03:32

标签: sql

我有两个桌子

第一个是“博客”表:

+----+--------+--------+
| id | title  | status |
+----+--------+--------+
|  1 | blog 1 |      1 |
|  2 | blog 2 |      1 |
+----+--------+--------+

第二个是blog_activity:

状态1为:创建 状态2为:打开

+----+---------+--------+------------+
| id | blog_id | status |    date    |
+----+---------+--------+------------+
|  1 |       1 |      1 | 2019-09-09 |
|  2 |       2 |      1 | 2019-09-10 |
|  2 |       2 |      2 | 2019-09-11 |
+----+---------+--------+------------+

我希望博客的记录不与博客表的所有详细信息一起打开。

示例:

+----+---------+--------+------------+--------------------+
| id | blog_id | title  | blog.date  | blog_activity.date |
+----+---------+--------+------------+--------------------+
|  1 |       1 | blog 1 | 2019-09-09 | 2019-09-09         |
+----+---------+--------+------------+--------------------+

2 个答案:

答案 0 :(得分:1)

我想我会使用existsjoin

select b.*, ba.date as created_date
from blog b join
     blog_activity ba
     on ba.blog_id = b.id and ba.status = 1
where not exists (select 1
                  from block_activity ba2
                  where ba2.blog_id = b.id and ba2.status = 2
                 );

这避免了聚合,并且可以在blog_activity(blog_id, status)上使用索引。

答案 1 :(得分:0)

一种方法使用聚合:

SELECT
    ba.id,
    ba.blog_id,
    b.title,
    ba.date
FROM blog b
INNER JOIN blog_activity ba
    ON b.id = ba.blog_id
INNER JOIN
(
    SELECT blog_id
    FROM blog_activity
    GROUP BY blog_id
    HAVING COUNT(CASE WHEN status = 2 THEN 1 END) = 0
) t
    ON b.id = t.blog_id;

Demo

别名为t的子查询查找所有不是与之关联的打开状态的博客。在这种情况下,只有blog_id = 1符合此条件。