INNER JOIN + LEFT JOIN(双重过滤)

INNER JOIN + LEFT JOIN (Double filtering)

我正在尝试过滤我的 table,其中用户在一个 table 中有一行,而在另一个中没有一行。这是我的 table 结构:

下面是 SQL Fiddle: http://sqlfiddle.com/#!9/6e27ed/2

CREATE TABLE users (
   user_id INT(11) AUTO_INCREMENT,
   name VARCHAR(25),
   PRIMARY KEY(user_id)
);

CREATE TABLE photos (
   photo_id INT(11) AUTO_INCREMENT,
   user_id INT(11) NOT NULL,
   PRIMARY KEY(photo_id)
);

CREATE TABLE blocked (
   user_id INT(11) NOT NULL,
   blocked_id INT(11) NOT NULL
);

INSERT INTO users (name) 
VALUES ('returned'), ('not returned'), ('not returned'), ('not returned');

INSERT INTO photos (user_id) 
VALUES (1), (2);

INSERT INTO blocked (user_id, blocked_id) 
VALUES (4, 2);

这是我正在尝试的查询:

SELECT u.*, min(p.photo_id)
FROM users u
INNER JOIN photos p using(user_id)
LEFT JOIN blocked b ON b.user_id = 4 AND b.blocked_id = u.user_id 
WHERE u.user_id != 4
GROUP BY u.user_id
LIMIT 9;

示例数据非常清楚结果应该是什么,因为本示例中 "name" 字段填充为 "returned", "not returned" ,仍然返回 user-id 2,但他应该是被 LEFT JOIN 删除,因为用户 ID 4 在被阻止的 table 的 blocked-id 字段中有用户 ID 2。

预期 结果来自 table:

+---------+----------+-----------------+
| user_id |   name   | min(p.photo_id) |
+---------+----------+-----------------+
|       1 | returned |               1 |
+---------+----------+-----------------+

已收到 个查询结果:

+---------+--------------+-----------------+
| user_id |     name     | min(p.photo_id) |
+---------+--------------+-----------------+
|       1 | returned     |               1 |
|       2 | not returned |               2 |
+---------+--------------+-----------------+

很难回答这个问题,因为我看到您正在比较 blocked_id=user_id,尽管在已屏蔽的 table 中您也有一个 user_id 列。只有你自己知道。

但请考虑以下内容

SELECT u.*, min(p.photo_id),b.*
FROM users u
INNER JOIN photos p using(user_id)
LEFT JOIN blocked b ON b.user_id = 4 AND b.blocked_id = u.user_id 
WHERE u.user_id != 4 and b.user_id is null
GROUP BY u.user_id
LIMIT 9;

+---------+----------+-----------------+---------+------------+
| user_id | name     | min(p.photo_id) | user_id | blocked_id |
+---------+----------+-----------------+---------+------------+
|       1 | returned |               1 |    NULL |       NULL |
+---------+----------+-----------------+---------+------------+

它通过显示添加为第 4 列和第 5 列的 b.* 列来打开声纳。并且稍微弄乱了 where 子句。

编辑:

已为生产清理

SELECT u.*, min(p.photo_id)
FROM users u
INNER JOIN photos p using(user_id)
LEFT JOIN blocked b ON b.user_id = 4 AND b.blocked_id = u.user_id 
WHERE u.user_id != 4 and b.user_id is null
GROUP BY u.user_id
LIMIT 9;

我认为您希望 WHERE b.blocked_id IS NULL 至 return 未被用户 4

阻止的用户

你可以试试这个..

SELECT u.*, min(p.photo_id)
FROM users u
INNER JOIN photos p using(user_id)
LEFT JOIN blocked b ON b.blocked_id = u.user_id 
GROUP BY u.user_id having min(p.photo_id)<=all(select min(p.photo_id) FROM users u
INNER JOIN photos p using(user_id)
LEFT JOIN blocked b ON b.blocked_id = u.user_id 
GROUP BY u.user_id)
;