MYSQL外连接,不返回不匹配的行

时间:2011-12-19 19:03:37

标签: mysql outer-join

我在db

中有这两个表
describe external_review_sources;
+-------+--------------+------+-----+---------+----------------+
| Field | Type         | Null | Key | Default | Extra          |
+-------+--------------+------+-----+---------+----------------+
| ersID | int(11)      | NO   | PRI | NULL    | auto_increment |
| name  | varchar(50)  | NO   | UNI | NULL    |                |
| logo  | varchar(255) | NO   |     | NULL    |                |
+-------+--------------+------+-----+---------+----------------+
3 rows in set (0.00 sec)

describe listing_external_review_source_rel;
+---------+--------------+------+-----+---------+----------------+
| Field   | Type         | Null | Key | Default | Extra          |
+---------+--------------+------+-----+---------+----------------+
| lersrID | int(11)      | NO   | PRI | NULL    | auto_increment |
| bid     | int(10)      | NO   |     | NULL    |                |
| url     | varchar(255) | NO   |     | NULL    |                |
| ersID   | int(11)      | YES  |     | NULL    |                |
| active  | int(10)      | NO   |     | NULL    |                |
| order   | int(10)      | NO   |     | NULL    |                |
+---------+--------------+------+-----+---------+----------------+
6 rows in set (0.00 sec)

我以这种方式查询这些表:

    SELECT * 
    FROM 
        listing_external_review_source_rel 
        RIGHT JOIN
        external_review_sources USING(ersID)
    where bid=902028 or bid IS NULL;

+-------+---------------+------+---------+--------+-------+--------+-------+
| ersID | name          | logo | lersrID | bid    | url   | active | order |
+-------+---------------+------+---------+--------+-------+--------+-------+
|     1 | G1            | a    |      17 | 902028 | url11 |      1 |     0 |
|     2 | D1            | b    |      18 | 902028 | url22 |      0 |     0 |
+-------+---------------+------+---------+--------+-------+--------+-------+
2 rows in set (0.00 sec)

正如您所看到的结果显示为出价= 902028,如果出价如866696,则不存在于listing_external_review_source_rel中,则结果为空

SELECT * 
FROM listing_external_review_source_rel 
     RIGHT JOIN external_review_sources USING(ersID) 
where bid=866696  or bid IS NULL;
Empty set (0.00 sec)

我希望结果如下:

+-------+---------------+------+---------+--------+-------+--------+-------+
| ersID | name          | logo | lersrID | bid    | url   | active | order |
+-------+---------------+------+---------+--------+-------+--------+-------+
|     1 | G1            | NULL |     NULL| NULL   | NULL  |   NULL |  NULL |
|     2 | D1            | NULL |     NULL| NULL   | NULL  |   NULL |  NULL |
+-------+---------------+------+---------+--------+-------+--------+-------+
2 rows in set (0.00 sec)

这就是我使用“或出价IS NULL”的条件。

我做错了什么,查询会给我这个结果?我基本上对我的结果中也有不匹配的行感兴趣。

3 个答案:

答案 0 :(得分:4)

大多数人都使用LEFT JOIN,所以我将其重写为更标准:

SELECT *
FROM external_review_sources a LEFT JOIN
     listing_external_review_source_rel b ON a.ersID=b.ersID AND bid=866696;

请记住,外部联接会返回ON条件匹配的所有行,而不会返回NULL。在这种情况下,您的匹配条件不仅仅是ersID

答案 1 :(得分:1)

试试这个

SELECT * FROM 
    external_review_sources e
    LEFT JOIN
    listing_external_review_source_rel r ON e.ersID = r.ersID AND r.bid = 866696
WHERE
    r.bid IS NULL;

在“外部表”上过滤时,过滤器需要是派生表或JOIN中,因为您希望在WHERE之前进行过滤(逻辑上)。此外,最佳做法是使用LEFT JOIN以获得清晰度。

使用派生表

SELECT * FROM 
    external_review_sources e
    LEFT JOIN
    (
     SELECT * 
     FROM listing_external_review_source_rel
     WHERE bid = 866696
    ) r USING (ersID)
WHERE
    r.bid IS NULL;

答案 2 :(得分:0)

以这种方式尝试,将bid列的测试移出WHERE子句并进入JOIN:

SELECT * 
    FROM listing_external_review_source_rel ler
        RIGHT JOIN external_review_sources ers   
            ON ler.ersID = ers.ersID
                AND ler.bid=866696;