MySQL为多个条件返回不同的结果

时间:2009-12-03 18:16:04

标签: sql mysql join

我有包含列表,类别的表格以及将它们相互映射的表格。因此,列表可以放在多个类别中。如下所示:

listings table
    id
    title
    etc

categories table
    id
    category_name
    etc

map table
    listing_id
    category_id

当我需要获取单个类别中列表的所有信息时(在本例中为id为18的类别),以下工作正常:

SELECT *
FROM (`listings`, `map`)
WHERE `map`.`category_id` = 18
AND map.listing_id = listings.id 

我的问题是如何进行类似类型的查询,但现在我需要找到两个类别内的不同列表。例如,如果我只需要返回category_id = 18 AND category_id = 20中的那些不同列表,该怎么办?这需要某种类型的加入吗?

3 个答案:

答案 0 :(得分:2)

是的,你会想要(另一个)加入。我认为以下应该这样做:

SELECT lst.`id`, lst.<column>, ...
FROM `listings` lst, `map` m, `map` m2
WHERE m.`category_id` = 18 AND m2.`category_id` = 20
AND m.`listing_id` = lst.`id`
AND m2.`listing_id` = lst.`id`

另一个版本,受到Germ建议的启发,但这个版本有效(请注意,为了清晰起见,我将id替换为category_id):

select l.listing_id
from listings l
join (select m.listing_id, count(*) as cnt from map m where
    m.category_id in (18,20)
    group by m.listing_id) cat_matches
    on cat_matches.listing_id = l.listing_id
where cat_matches.cnt = 2; -- 2 is the number of distinct categories to match

丑陋,是吗?并且子选择可能不那么有效......但是:


select l.listing_id
from listings l
join map m on l.listing_id=m.listing_id
where m.category_id in (18,20)
group by l.listing_id
having COUNT(*)=2;

您可以通过获取所需的所有行然后过滤它们来消除该子选择。请注意,此解决方案假定映射表中的行是唯一的(应该是这种情况,因为应在listing_idcategory_id上定义PK。)

答案 1 :(得分:1)

这应该有效

select * from listings l
join map m on m.listing_id = l.id
join categories c on c.id = m.category_id
where c.id in (18, 20)

答案 2 :(得分:0)

这个怎么样......

select * from listings l, map m, categories c
where l.id = m.listing_id
and m.category_id = c.id
and (c.id = 18 
or c.id = 20)

select * from listings l, map m, categories c
where l.id = m.listing_id
and m.category_id = c.id
and c.id in (18, 20)