2010-09-24 42 views
7

我想知道如何通過匹配的標籤數量來匹配具有匹配標籤的商品。通過匹配的標籤數量來匹配標籤訂購商品

比方說,你有三個MySQL表:

  • tags(tag_id, title)
  • articles(article_id, some_text)
  • articles_tags(tag_id, article_id)

現在讓我們假設你有四篇文章,其中:

​​有標籤「幽默「,」f unny「和」搞笑「。

article_id = 2標籤「有趣」,「愚蠢」和「愚蠢」。

article_id = 3標籤爲「有趣」,「愚蠢」和「愚蠢」。

article_id = 4有標籤「完全嚴重」。

您需要至少找到一個匹配標籤,才能找到與article_id = 2相關的所有文章,並按照最佳匹配順序返回結果。換句話說,article_id = 3應該是第一個,​​秒,article_id = 4應該不會出現。

這是可以在SQL查詢或單獨執行的東西,還是更適合像Sphinx這樣的東西?如果前者,應該完成哪種查詢,以及應該爲最高性能結果創建什麼類型的索引?如果後者,請擴大。

回答

10

嘗試這樣:

select article_id, count(tag_id) as common_tag_count 
from articles_tags 
group by tag_id 
where tag_id in (
    select tag_id from articles_tags where article_id = 2 
) and article_id != 2 
order by common_tag_count desc; 

語法可能需要MySQL的一個小調整。

或這一個,實際工作:;-)

SELECT at1.article_id, Count(at1.tag_id) AS common_tag_count 
FROM articles_tags AS at1 INNER JOIN articles_tags AS at2 ON at1.tag_id = at2.tag_id 
WHERE at2.article_id = 2 
GROUP BY at1.article_id 
HAVING at1.article_id != 2 
ORDER BY Count(at1.tag_id) DESC; 
+0

第二種語法非常棒,並且完全按照我需要的方式工作。非常感謝! – 2010-09-24 07:20:20

2

類似的東西:

SELECT a.* 
FROM articles AS a 
INNER JOIN articles_tags AS at ON a.id=at.article_id 
INNER JOIN tags AS t ON at.tag_id = t.id 
WHERE t.title = 'funny' OR t.title = 'goofy' OR t.title = 'silly' AND a.id != <article_id> 
GROUP BY a.id 
ORDER BY COUNT(a.id) DESC 

只需通常的指標,假設articles_tags有(article_id的,TAG_ID)PK,和index on tags.title