在1个查询中连接多个表,导致重复

时间:2015-11-18 18:55:34

标签: mysql sql database

我有一张名为' games'。

的表格

游戏可以有多个标签和多个作者。每个标签或作者都可以属于多个游戏。

我想跟踪每个单独的标签和每个单独的作者使用单独的表,所以我有以下表格及其列:

游戏:id,... game_tags:id,name game_tags_map:id,game_id,tag_id game_authors:id,name game_authors_map:id,game_id,author_id

如果我想获得包含所有标签的游戏​​记录,请执行以下查询:

SELECT g.*,
GROUP_CONCAT(gt.name) as tag_names, GROUP_CONCAT(gt.id) as tag_ids
FROM games g    
INNER JOIN game_tags_map gtm ON g.id = gtm.game_id
INNER JOIN game_tags gt ON gtm.tag_id = gt.id    
WHERE g.id = 1
GROUP BY g.id

我得到了:

id ... category_names    category_ids
1  ... 3D,2 Player       2,1

正如我想要的那样。但是,为了获得author_names和author_ids,我还要执行什么? 我试试:

SELECT g.id,
GROUP_CONCAT(gt.name) as tag_names, GROUP_CONCAT(gt.id) as tag_ids,
GROUP_CONCAT(ga.name) as author_names, GROUP_CONCAT(ga.id) as author_ids
FROM games g    
INNER JOIN game_tags_map gtm ON g.id = gtm.game_id
INNER JOIN game_tags gt ON gtm.tag_id = gt.id
INNER JOIN game_authors_map gam ON g.id = gam.game_id
INNER JOIN game_authors ga ON gam.author_id = ga.id    
WHERE g.id = 1
GROUP BY g.id

但我明白了:

id ... category_names           category_ids      author_names          author_ids
1  ... 3D,2 Player,3D,2 Player  2,1,2,1           Tom,Dave,Tom,Dave       1,2,1,2

换句话说,一切都翻倍。 另外我注意到它需要的时间比我预期的要长10倍。第一个查询需要0.001秒,第二个查询需要0.008秒。

我做错了什么?

1 个答案:

答案 0 :(得分:0)

最简单的解决方案是在GROUP_CONCAT上使用distinct:

SELECT
  g.id,
  GROUP_CONCAT(DISTINCT gt.name) as tag_names,
  GROUP_CONCAT(DISTINCT gt.id) as tag_ids,
  GROUP_CONCAT(DISTINCT ga.name) as author_names,
  GROUP_CONCAT(ga.id) as author_ids
FROM ....

另一个解决方案是在子查询中使用GROUP_CONCAT,如下所示:

SELECT
  g.id,
  tag_names,
  author_names,
  ...
FROM
  games g INNER JOIN (SELECT id, GROUP_CONCAT(...) AS tag_names
                      FROM ...
                      GROUP BY id) t
  ON g.id=t.id
  INNER JOIN (SELECT id, GROUP_CONCAT(...) AS author_names
              FROM ...
              GROUP BY id) a
  ON g.id = a.id