这些是3张桌子(水手,船只,储备),我想知道保留两条夹层船(101,102)的水手.BID应该由电脑计算
`select * from sailors
where sid in(select sid from reserves
inner join boats on reserves.bid = boats.bid
where boats.bname='Interlake')`
查看表格https://i.stack.imgur.com/hfHpH.png图片的链接 或链接到pdf表格http://www.cs.toronto.edu/~avaisman/csc343summer/tutorials/Tutorial_5.pdf
结果= dustin luber horatio 期待=尘土飞扬 谢谢你的帮助
答案 0 :(得分:0)
您可以使用以下
<强>解释强>
查询
declare @boat varchar(50) = 'Interlake'
;with report as (
select bname,count(*) as [Count]
from boats b
where b.bname=@boat
group by b.bname
), summary as(
select s.sname, b.bname, count(*) as [Count]
from sailors s
inner join reserves r on r.sid = s.sid
inner join boats b on b.bid = r.bid
where b.bname=@boat
group by s.sname,b.bname
)
select s.*
from summary s
inner join report r on r.bname = s.bname and r.[Count] = s.[Count]
这是一个有效的demo
希望这会对你有所帮助
答案 1 :(得分:0)
以下SQL将构建临时表变量,填充它们然后使用连接来向您显示哪些水手已经预留了InterLake船。
- 构建水手临时表变量并插入测试数据
declare @sailors table
([sid] int
,[name] varchar(50))
insert into @sailors
([sid],[name])
values
(1,'Sailor One'),
(2,'Sailor Two'),
(3,'Sailor Three')
- 构建临时表变量并插入测试数据
declare @boats table
(bid int
,[name] varchar(50))
insert into @boats
(bid,[name])
values
(1,'10 foot John Boat'),
(2,'14 foot John Boat'),
(3,'18 foot Ski Boat'),
(4,'Interlake')
- 构建保留临时表变量并插入测试数据
declare @reserves table
(rid int
,[sid] int
,bid int)
insert into @reserves
(rid,[sid],bid)
values
(1, 1, 4),
(2, 3, 1),
(3, 2, 4)
- 查询选择哪些水手已预留Interlake船
select s.name as Sailor
,b.name as Boat
from @sailors s
inner join @reserves r on r.[sid] = s.[sid]
inner join @boats b on b.bid = r.bid
where b.name = 'InterLake'
- 结果
Sailor Boat
Sailor One Interlake
Sailor Two Interlake
答案 2 :(得分:0)
首先,我们将加入两个表格,其中水手sid匹配储备sid和出价为101或102的地方,因为这是Interlake
的出价。如果你想通过where bname = interlake
来做,你将把船加入储备。这是您使用inner join
在原始查询中完成的操作。我选择使用左:
select s.*
from sailors s
left join reserves r on r.sid = s.sid
where r.bid in (101, 102)
现在我有所有人都保留了101或102号船。我想过滤掉那些只有两者的人。在这种情况下,我想从我的过滤结果中查询。我决定使用派生表,但你也可以使用cte。
类似的东西:
select *
from
(select s.*
from sailors s
left join reserves r on r.sid = s.sid
where r.bid in (101, 102)) t1 --t1 is the alias
但我不希望这个过滤表中的所有内容。我想要名字。
select sname
from
(select s.*
from sailors s
left join reserves r on r.sid = s.sid
where r.bid in (101, 102)) t1
但我只想要那些租用101和102的人的名字。在这种情况下,如果按照名字计算,这意味着如果你的数量大于1,你只能租用两者:
select sname --select the column of names I want
,count(sname) as total --here's the count of names, completely optional
from
(select s.*
from sailors s
left join reserves r on r.sid = s.sid
where r.bid in (101, 102)) t1
group by sname --anything you use an aggregation you'll need to likely group by something
having count(sname) > 1 --my filter after I group my names
以下是您可以使用的rextester示例。
答案 3 :(得分:0)
SELECT DISTINCT S.SID,S.SNAME,S.RATING,S.AGE
FROM SAILORS S,RESERVES R,BOATS B
WHERE S.SID=R.SID AND R.BID=B.BID
AND NOT EXISTS
((SELECT B.BID
FROM BOATS B WHERE B.BNAME NOT LIKE '%INTERLAKE%')
EXCEPT
(SELECT R.BID
FROM RESERVES R
WHERE R.SID=S.SID))