SQL列出了不存在的对象

时间:2018-04-05 12:18:23

标签: sql

我有以下问题。 两张桌子。产品表和库存表。

在产品表中列出了所有可能的产品,在库存中列出了每个商店的当前库存

e.g。 库存表

ProductID     Stock     StoreID
1             10        1
2             10        1
3             10        1
1             10        2

产品表

ProductID     Product     
1             Bananas        
2             Apples 
3             Oranges
4             Kiwi

我想要的是商店没有库存的产品清单。 在该示例之后,期望的结果将是

Store ProductID  Product
1     4          Kiwi 
2     2          Apples
2     3          Oranges 
2     4          Kiwi

现在我尝试了几种来自左连接的方法,而不是存在但不存在但尚未找到解决方案。 E.g。

SELECT * 
FROM Inventory t1 
left join Product t2 ON t2.ProductID = t1.ProductID 
WHERE t2.ProductID IS NULL 

但这不会返回任何内容

请帮忙。

谢谢

2 个答案:

答案 0 :(得分:2)

解决您的问题:

FOR MySQL 以及 MSSQL

SELECT i.storeId,p.ProductId, p.product
FROM Product p
CROSS JOIN (
            SELECT Distinct storeId 
            FROM Inventory) i
LEFT JOIN Inventory iv
ON p.productID = iv.productId AND i.storeId = iv.storeId
WHERE iv.storeId IS NULL;

<强>输出:

storeId  ProductId  product
 1        4          Kiwi
 2        2          Apples
 2        3          Oranges
 2        4          Kiwi

点击演示链接:

  

http://sqlfiddle.com/#!9/71a854/9

CROSS JOIN:

CROSS JOIN生成了一个结果集,当没有WHERE子句与CROSS JOIN一起使用时,该结果集是两个关联表的行的乘积。

在此连接中,如果CROSS JOIN没有引入条件,则通过将第一个表的每一行与第二个表中的所有行相乘来显示结果集。

这种结果称为笛卡尔积。

下面的图片将为您提供更清晰的图片:

enter image description here

来源:https://www.w3resource.com/mysql/advance-query-in-mysql/mysql-cross-join.php

答案 1 :(得分:0)

您的方法应该有效,尽管仅从第一个表中选择列是有意义的。第一个表应该是产品表:

SELECT p.*
FROM Product p LEFT JOIN
     Inventory i 
     ON i.ProductID = p.ProductID
WHERE i.ProductID IS NULL;

您的版本会返回Product表中没有的所有库存产品。如果您的数据格式正确,那么这是不可能的。

编写查询的另一种方法是使用NOT EXISTS

select p.*
from product p
where not exists (select 1 from inventory i where i.productid = p.productid);

这个版本(如果你有inventory(productid)的索引,应该会有非常好的表现)更接近你表达问题的方式。