2

我有 2 张桌子:

广告:

+------+---------------+
|  ID  |  Name         |
+------+---------------+
| 1    |   Item 1      |
| 2    |   Item 2      |
| 3    |   Item 3      |
| 4    |   Item 4      |
| 5    |   Item 5      |
+------+---------------+

分配广告:

+------+-----------+--------------+
|  ID  |   ad_id   |  location    |
+------+-----------+--------------+
|  1   |    3      |  place 1     |
|  2   |    2      |  place 2     |
|  3   |    1      |  place 3     |
+------+-----------+--------------+

如你看到的; 广告 1,2 和 3 都分配到一个位置。我需要的是一个查询,它获取表ads中未分配的所有行assigned_ads

4

5 回答 5

4

您需要使用 LEFT OUTER JOIN 来执行此操作,如下所示:

SELECT * 
FROM ads a
LEFT JOIN assigned_ads aa ON a.ID = aa.ad_id
WHERE aa.location IS NULL
于 2011-10-12T12:00:13.593 回答
1

You can also use the NOT EXISTS operator:

SELECT * 
FROM ads a
WHERE NOT EXISTS
(SELECT * FROM assigned_ads aa WHERE a.ID = aa.ad_id)
于 2011-10-12T12:07:44.627 回答
1

您需要的关系运算符是 semi Difference aka antijoin

大多数 SQL 产品缺少显式的半连接运算符或关键字。标准 SQL-92 没有一个(它有一个MATCH (subquery)semijoin 谓词,但是,虽然很容易不这么想,但语义NOT MATCH (subquery)与半差分不同;FWIW 真正的关系语言教程 D成功地使用了NOT MATCHING半差分)。

半差分当然可以使用其他 SQL 谓词来编写。最常见的是:在WHERE子句中测试空值的外连接,紧随其后的是EXISTSor IN (subquery)。如果您的 SQL 产品支持并且再次取决于数据(特别是当两个表的标题相同时),使用EXCEPT(相当于在 Oracle 中)是另一种可能的方法。MINUS

就个人而言,我更喜欢EXISTS在 SQL 中使用半差分连接,因为连接子句在书面代码中更接近,并且不会导致连接表上的投影,例如

SELECT *
  FROM ads 
 WHERE NOT EXISTS (
                   SELECT * 
                     FROM assigned_ads
                    WHERE ads.ID = assigned_ads.ID
                  );

与(与外连接方法相同)一样,如果子查询中的子句涉及空值,IN (subquery)则需要格外小心(提示:如果子查询中的子句由于存在空值而评估为 UNKNOWN,那么它将被强制为 FALSE ,这可能会产生意想不到的结果)。WHEREWHEREEXISTS

于 2011-10-13T09:16:56.787 回答
0

just user left join query and match the left table id to null. you query should look like this

select * from ads ad left join assigned_ad a_ad ON a_ad.ad_id = ad.id where a_ad.id is null

For more information about left join consult here

于 2011-10-12T12:07:09.393 回答
0

尝试这个:

SELECT * 
FROM ads a
WHERE a.id NOT IN (SELECT ad_id FROM assigned_ads)
于 2011-10-12T12:01:11.993 回答