我有三个数据库表:
故事
类别
StoryCategory
注意:故事和类别具有多对多关系(一个故事可以有多个类别,一个类别可以有多个故事)所以我创建了StoryCategory。此外,一个故事可以没有类别。
我还有一个网页(我使用剃须刀):
<form action="" method="get">
<label for="keyword">Keyword:</label>
<input name="keyword" type="text" value="@Page.Keyword" />
<label for="category">Category:</label>
<select name="category">
<option value="">All</option>
@foreach(var category in Page.Categories)
{
<option value=@category.Id @(category.Id == Page.Category? "selected=selected" : "")>@category.Title</option>
}
</select>
<input type="submit" value="Search" />
</form>
为简单起见,此页面允许用户输入关键字以搜索特定故事,并且还允许用户选择故事所属的类别。
我无法找到附加到特定类别的故事的方法。这是我的第一个代码(忽略关注类别的关键字):
select s.title --columns will be added here such as name of category/ies, author etc.
from story as s
left join --left join so the uncategorized stories will not be excluded
storyCategory as sc
on s.id = sc.storyId
where sc.categoryId = @selectedCategory --this line is removed when there is no category selected
示例数据:
故事
id标题内容 1个火影忍者...... 2漂白...
分类
id标题 1幻想 2动作 3戏剧
StoryCategory
storyId categoryId 1 1 1 2 2 1
问题是,如果没有选定的类别,如果故事有多个类别,它也会多次出现:
naruto (fantasy)
naruto (action)
bleach (fantasy)
我实际上知道发生了什么,但我无法想出解决问题的最佳解决方案。
答案 0 :(得分:3)
使用DISTINCT关键字,左连接对您的WHERE条件无效
select DISTINCT
s.title --columns will be added here such as name of category/ies, author etc.
from story as s
join storyCategory as sc--left join so the uncategorized stories will not be excluded
on s.id = sc.storyId
where sc.categoryId = @selectedCategory --this line is removed when there is no category selected
如果您需要附加到每个故事的类别列表 - 请查看并检查下一个查询。适用于sql server:
DECLARE @Stories TABLE(Id INT IDENTITY PRIMARY KEY, NAME NVARCHAR(100) NOT NULL)
DECLARE @Categories TABLE(Id INT IDENTITY PRIMARY KEY, NAME NVARCHAR(100) NOT NULL)
DECLARE @Fork TABLE(StoryId INT NOT NULL, CategoryId INT NOT NULL, PRIMARY KEY(StoryId, CategoryId))
INSERT @Stories
VALUES ('Story1'), ('Story2'), ('Story3')
INSERT @Categories
VALUES ('Category1'), ('Category2'), ('Category3')
INSERT @Fork
VALUES(1,1), (1,2), (3,3), (2,3)
DECLARE @selectedCategory INT = 3
select
s.NAME,
(
SELECT c.Name + ','
FROM @Categories c
JOIN @Fork f ON f.CategoryId = c.Id AND f.StoryId = s.Id
ORDER BY c.Name
FOR XML PATH('')
) Categories
from @stories s
答案 1 :(得分:0)
如果您不将其限制为单个类别,请尝试以下方法:
select s.title,count(*) as NumCategories
from story as s
left join storyCategory as sc on s.id = sc.storyId
group by s.title
您还可以使用类似的内容查找某些类别,其中显示了类别的数量以及故事所在的第一个和最后一个(基于标题字符)类别
select s.title,count(*) as NumCategories,min(sc.title),max(sc.title)
from story as s
left join storyCategory as sc on s.id = sc.storyId
group by s.title