Mysql内部联接条目必须匹配多个条目

时间:2015-08-21 02:24:19

标签: mysql

我有两张桌子:

制品

ID    OTHER
1     foobar
2     more foobar

article_tags

ID    ARTICLE_ID    NAME
1     2             docs 
2     2             noob
3     1             docs

在上表中,我只想检索文章ID 2,因为它被docs和noob引用。 ID 1不应该返回,即使它与docs匹配,因为它也不匹配noob。

我想只检索包含docs和noob article_tags的文章。我尝试过使用内部联接:

SELECT articles.* FROM articles
INNER JOIN article_tags ON article_id = articles.id
WHERE article_tags.name = 'docs' AND article_tags.name = 'noob'
GROUP BY articles.id;

我知道这不起作用,因为article_tag名称不能同时是docs和noob,但我该如何正确地做到这一点?使用或返回正确的文章,但它也会返回仅包含docs或noob的所有文章。

1 个答案:

答案 0 :(得分:0)

当您想要向查询中的每一行添加更多列(即信息)时,JOIN会派上用场。 在这种情况下,子查询将更适合:

SELECT articles.*
FROM articles
WHERE id in (
    SELECT article_id
    FROM article_tags 
    WHERE article_tags.name IN('docs','noob')
    GROUP BY article_id HAVING COUNT(DISTINCT name) = 2
)

此处,子查询将返回具有docs and noob`标记的所有 article_id ,并通过以下方式执行:

  • 仅选择 article_tags 中具有相关标记名称的行
  • 通过 article_id (我们想要的值)对过滤的行进行分组,并仅保留存在两行或更多行*的值。

*:我刚刚注意到,如果 article_tags 有另一行 article_id = 1且 name = “docs”,那么文章“foobar”会出现在结果中,这是错误的。 我认为您可以使用正确的 PK article_tags 表中的唯一键来解决此问题,这会阻止在同一个 article_id中添加另一个具有相同名称的标记
或者,可能更好,将 article_tags 表分成两部分,创建一个单独的标记表。

相关问题