我希望供应各部分的供应商的SIDS。我无法理解本书给出的查询答案。
Suppliers(sid: integer, sname: string, address: string)
Parts(pid: integer, pname: string, color: string)
Catalog(sid: integer, pid: integer, cost: real)
假设您获得了以下数据库:
表:零件
PID
P1
P2
P3
表:目录
SID PID
S1 P1
S1 P2
S1 P3
S2 P1
它应输出S1,但我相信在给定的查询中,它将输出S1和S2。最后一个嵌套查询不会满足SID = 2吗?因为如果C1.sid = S2并且C.sid = S2并且C1.pid = P1并且P.pid = P1那么它将满足查询。
书的答案如下: SQL翻译:“C.Sid,其中不存在C.Sid未提供的部分”
SELECT C.sid
FROM Catalog C
WHERE NOT EXISTS (SELECT P.pid
FROM Parts P
WHERE NOT EXISTS (SELECT C1.sid
FROM Catalog C1
WHERE C1.sid = C.sid
AND C1.pid = P.pid)
)
答案 0 :(得分:1)
一个简单的矛盾证明'将证明查询永远不会返回S2。
对于返回S2的查询,第一个NOT EXISTS
将要求Parts
上的子查询产生零行。但肯定不是这种情况,因为该特定子查询返回S2未提供的所有部分(即P2和P3)。
答案 1 :(得分:1)
您应该将查询读作:
向我提供那些没有高估供应商的相应目录的供应商。您应该在这里从上到下阅读查询。想象一下Catalogs
表上的循环。获取第一行(S1,P1
)。为Parts
执行内循环,并检查S1
是否存在该部分。它存在。好。获取第二部分。它存在。获取第三部分。它存在。因此,对于第一行,不存在第一行中供应商的目录中不存在的这样的部分。获取第二行(S1,P2
)等...
答案 2 :(得分:0)
查询选择您在结果中不想要的sid(不存在的地方)。
所以查询选择S2(不是两者),因为你选择的所有sid都没有被选中,结果就是S1。
用简单的话说;你创建了一个你不想要最终结果的sid的列表。