JOIN而不是相关标签的子查询

时间:2010-12-19 14:28:08

标签: sql mysql join tagging subquery

我有三个表,bookmarkstagtaggingtagging是用于将标记链接到书签的关联表。我想选择相关的标签。当前查询需要花费很长时间才能运行,但我无法绕过可能替换选择所有标记有特定标记ID的相关书签的子查询的JOIN。

SELECT ta.name, count(*) 
FROM tagging t2 
JOIN tag ta ON t2.tag_id=ta.id  
WHERE t2.bookmark_id IN (
   SELECT bookmark_id 
   FROM tagging t1 
   WHERE t1.tag_id IN (1, 7) 
   GROUP BY t1.bookmark_id 
   HAVING COUNT(t1.id) = 2
) 
GROUP BY ta.id

以下是该查询的EXPLAIN的结果:

1   PRIMARY            ta  index PRIMARY    PRIMARY         8   NULL         3   
1   PRIMARY            t2  ref   tag_id_idx tag_id_idx      8   blinkz.ta.id 89   Using where
2   DEPENDENT SUBQUERY t1  index tag_id_idx bookmark_id_idx 8   NULL         71   Using where 

我有bookmark_id表中tag_idtagging字段的索引。 tag表有一个名为id

的主键

如何优化此查询,最好使用JOIN而不是子查询?

1 个答案:

答案 0 :(得分:2)

表现不佳是因为bug in MySQL很快就会被修复。在那之前尝试这个:

SELECT tag.name, COUNT(*) AS cnt
FROM tagging T1
JOIN tag
ON T1.tag_id = tag.id  
JOIN (
   SELECT bookmark_id 
   FROM tagging
   WHERE tag_id IN (1, 7) 
   GROUP BY bookmark_id 
   HAVING COUNT(id) = 2
) T2
ON T1.bookmark_id = T2.bookmark_id
GROUP BY tag.id

我假设(bookmark_id, tag_id)上有一个独特的约束。