我有两个相关的表,为了这个问题的目的,它将被称为posts
和tags
。 posts
包含各种帖子,例如在社区论坛系统中找到的帖子。 tags
包含一组唯一的标记,这些标记在服务器遇到系统中尚未存在的新标记时添加。每个标签只有一个条目。
posts
可以有多个标记,而tags
可以有多个帖子作为对它的引用。为了来回处理这些引用,我创建了一个表位于这两个表之间,称为posttags
。 posttags
包含对tag
ID和post
ID的引用。这就是维持多对多关系的方式。
现在,关于这个问题。我需要能够根据标签选择帖子。当只有一个标记要搜索时,这是一个简单的连接,但我对如何处理多个标记感到茫然。例如,我需要能够搜索数据库并获得具有列表中所有标记的结果(例如,“php,mysql,sql”),而不使用循环内的SQL或任何其他低性能选项。
我不知道该怎么做。有人能指出我正确的方向吗?
谢谢!
答案 0 :(得分:3)
您可以使用以下方法,3是请求标签的数量。
SELECT PostId
FROM posttags pt, tags t
WHERE p.Id = pt.PostId
AND t.Id = pt.TagId
AND tagname In ('php', 'mysql', 'sql')
group by PostId
having count(*) = 3
或者您可以按顺序对请求的标签进行排序并使用以下内容:
Select * from Posts p,
(
SELECT PostId, GROUP_CONCAT(tagname ORDER BY tag_name DESC SEPARATOR ' ') Tags
FROM posttags pt, tags t
WHERE p.Id = pt.PostId
AND t.Id = pt.TagId
GROUP BY PostId
)t 在哪里.PostId = p.Id AND t.Tags ='mysql php sql'
但您需要对标签进行排序
答案 1 :(得分:1)
如果您要选择在给定集中包含所有标记的帖子,您可以使用“计数”策略:
SELECT
p.*
FROM tags t
LEFT JOIN posttags pt
ON pt.tag_id = t.tag_id
LEFT JOIN posts p
ON p.post_id = pt.post_id
WHERE
tags.tag IN ('php', 'mysql', 'sql')
GROUP BY p.post_id
HAVING COUNT(tags.tag_id) = 3;
当然,如果你更改了套装,数字“3”应该改为套装中的元素数量。