我正在使用SQL Server 2008 R2
我正在尝试编写一个只返回我需要的查询。我将放入一个MovieID并获取所有类型的列表。如果影片代表特定类型(在联结表中有相关记录),则Checked值将为1.如果不是,则为0.
我的结果集应如下所示:
GenreID Genre Checked
1 ABC 0
2 DEF 1
3 HIJ 0
4 KLM 1
My First表名为Genres。它看起来像这样:
GenreID Genre
1 ABC
2 DEF
3 HIJ
4 KLM
我的第二张桌子名为电影。它看起来像这样:
MovieID Title
1 Blah
2 Foo
3 Carpe
4 Diem
我的第三个表是名为Movies_Genres的联结表。它看起来像这样:
MovieID GenreID
1 2
1 1
1 4
2 1
2 3
3 4
4 1
我通常会做几个查询和几个循环来处理这个问题,但我想让数据库在这里完成工作。如何调整我的查询,以便只需一个查询即可获得所需的结果集?
这是起始查询:
SELECT GenreID,
Genre
FROM Genres
先谢谢你的帮助!!!
答案 0 :(得分:3)
SELECT g.GenreID, g.Genre, Checked = CASE WHEN EXISTS
(SELECT 1 FROM dbo.Movies_Genres AS mg
INNER JOIN dbo.Movies AS m
ON mg.MovieID = m.MovieID
WHERE mg.GenreID = g.GenreID
AND m.MovieID = @MovieID) THEN 1 ELSE 0 END
FROM dbo.Genres AS g
ORDER BY g.GenreID;
如果dbo.Movies_Genres(MovieID, GenreID)
上有唯一约束或主键,那么这可以是:
SELECT g.GenreID, g.Genre, Checked = COUNT(mg.GenreID)
FROM dbo.Genres AS g
LEFT OUTER JOIN dbo.Movies_Genres AS mg
ON g.GenreID = mg.GenreID
AND mg.MovieID = @MovieID
GROUP BY g.GenreID, g.Genre;
...因为任何类型的计数在给定@MovieID
的情况下只能是0或1。
答案 1 :(得分:2)
使用CASE非常直接;
SELECT DISTINCT g.GenreID, g.Genre,
CASE WHEN mg.MovieID IS NULL THEN 0 ELSE 1 END Checked
FROM Genres g
LEFT JOIN Movies_Genres mg
ON g.GenreID=mg.GenreID
AND mg.MovieId=@MovieID;
演示here。
编辑:如果在Movies_Genres中保证条目是唯一的,您可以选择删除DISTINCT。
答案 2 :(得分:1)
@MovieID
是要过滤的电影。
SELECT Genres.GenreID,
Genres.Genre,
CASE WHEN (Movies_Genres.GenreID IS NULL)
THEN 0
ELSE 1
END AS Checked
FROM Genres LEFT JOIN
Movies_Genres ON Movies_Genres.GenreID = Genres.GenreID AND
MovieID = @MovieID