在WHERE IN条件下返回的行

时间:2015-08-22 08:29:19

标签: mysql sql

我有一个SQL查询,如:

select gift.id as giftId, gift.title, count(vouchercode.id) as stock 
from gift 
inner join vouchertemplate 
left join vouchercode 
on gift.voucherTemplate = vouchertemplate.id 
and vouchertemplate.id = vouchercode.template 
and vouchercode.given = 0 
and gift.id in (5, 6, 7) 
group by gift.id 

我希望所有行都gift.id5,6,7之一,但我也会获得4行。这是为什么?

2 个答案:

答案 0 :(得分:2)

你已离开加入。你需要:

select gift.id as giftId, gift.title, count(vouchercode.id) as stock 
from gift 
inner join vouchertemplate 
left join vouchercode 
on gift.voucherTemplate = vouchertemplate.id 
and vouchertemplate.id = vouchercode.template 
and vouchercode.given = 0 
where gift.id in (5, 6, 7) 
group by gift.id 

当您将其置于JOIN条件时 - 它仅用于连接。出于这个原因,你得到 4 。你必须把它放在WHERE条款中。

如果此查询与您的业务逻辑不对应,请详细说明重新设计查询所需的结果类型。

答案 1 :(得分:0)

当您编写join时,您应该在每个on子句之间的每个表之间放置条件,在join个句子中,在on个句子中。结束。实际上,大多数数据库(和ANSI)都需要这种语法。

这实际上并不能解决您的问题。这是由on子句而不是where子句中的条件引起的:

select g.id as giftId, g.title, count(vc.id) as stock 
from gift g inner join
     vouchertemplate vt
     on g.voucherTemplate = vt.id left join
     vouchercode vc
     on vt.id = vc.template and vc.given = 0 
where g.id in (5, 6, 7) 
group by g.id ;

left join保留第一个表中的所有记录,无论on条件评估是否为真。因此,对第一个表进行过滤对left join没有影响。同样,对第二个表的过滤对right join无效。

解决方案是将条件放在where子句中的第一个表中。

还要注意表别名的使用,以便查询更容易编写和阅读。