以下是我正在运行的大型查询的代码段,该代码会对装满产品的表执行搜索。此片段不会将某些产品排除在结果中,除非它被覆盖(标记ID已指定,例如,制定了搜索条件)。
这里有几个标签ID及其名称:
标签ID 576 ='圣诞老人'
标签ID 123 ='圣诞节'
所以基本上下面将排除'tags_gifts_occasion_specific'表中的所有产品,除非它们的标签ID为576('Santa')。
AND NOT EXISTS (
SELECT *
FROM tags_gifts_occasion_specific
WHERE tags_gifts_occasion_specific.tag_id != '576'
GROUP BY tags_gifts_occasion_specific.gift_id
)
简单正确....
但问题是如果相同的产品在此表中但是应用了不同的标签ID ...例如它也在那里用于标记'Christmas'。
当然,添加'AND tags_gifts_occasion_specific.tag_id!='123'会很容易,但是查询不知道它不应该查找哪些附加ID - 只有已经搜索过的ID。 / p>
我一直在玩类似以下的东西,但不成功。我以为我可以计算gift_id的出现次数,如果已经找到了,那就再忽略了 - 任何新的输入都会非常感激。
AND NOT EXISTS (
SELECT * , COUNT( * ) AS no_gifts
FROM tags_gifts_occasion_specific
WHERE tags_gifts_occasion_specific.tag_id != '576'
HAVING no_gifts < 1
GROUP BY tags_gifts_occasion_specific.gift_id
)
**关于BUG命令的进一步细节**
所以bug的顺序如下。如果有人搜索“婚礼”和'bridemaid'礼品,婚礼或新娘礼品应该与首先显示的匹配返回,然后其余的基于受欢迎程度。这适用于'tags_gifts_occasion_specific'表中没有礼物的所有搜索。
SELECT gifts.affiliate_id, gifts.gift_id, gifts.gift_title, gifts.gift_price, gifts.gift_image, gifts.gift_slug
FROM gifts
LEFT JOIN tags_gifts_occasion_specific AS os ON gifts.gift_id = os.gift_id
LEFT JOIN tags_gifts ON tags_gifts.gift_id = gifts.gift_id
LEFT JOIN tags ON tags.id = tags_gifts.tag_id
LEFT JOIN popularity ON popularity.gift_id = gifts.gift_id AND popularity.tag_id = tags.id
WHERE published = '1' AND in_seekgifts = '1'
AND ( (tags_gifts.tag_id = '576' OR tags_gifts.tag_id = '340') )
AND NOT EXISTS (
SELECT * FROM tags_gifts_occasion_specific x WHERE x.gift_id = gifts.gift_id
AND NOT EXISTS(
SELECT * FROM tags_gifts_occasion_specific x1 WHERE x.gift_id = x1.gift_id AND ( tag_id IN (576) OR tag_id in (340) ) )
)
GROUP BY gifts.gift_id
ORDER BY COUNT(*) DESC , popularity.popularity DESC, gifts.gift_popularity DESC, gifts.gift_id DESC
结果的实例: http://www.seekgifts.co.uk/wedding_bridesmaid/
我认为正在发生的事情是它可以看到顶部的产品位于tags_gifts_occasion_specific表中,用于多个标签,因此按照在此表中找到的次数进行排序。不确定如何绕过这个?
答案 0 :(得分:1)
据我所知,有一个包含产品的表格,每个产品都有一个带标签的表格
该查询有望跳过具有某些标记的产品,并包含不具备这些标记的产品。
例如:
产品
| PRODUCT_ID | PRODUCT_NAME |
|------------|--------------|
| 1 | Product 1 |
| 2 | Product 2 |
| 3 | Product 3 |
| 4 | Product 4 |
| 5 | Product 5 |
<强>代码
| PRODUCT_ID | TAG |
|------------|--------------|
| 1 | Santa |
| 1 | Christmas |
| 2 | Christmas |
| 3 | Santa |
| 4 | Christmas |
| 4 | Exclude |
| 4 | Dont exclude |
| 5 | Christmas |
| 5 | Dont exclude |
我们希望跳过标记为Santa
和Exclude
的rpoducts
在上面的示例中,我们要跳过产品1,3和4,并包含产品2,5。
我们可以使用以下相关子查询
来实现SELECT * from products p
WHERE
NOT EXISTS(
SELECT 1 FROM tags t
WHERE t.product_id = p.product_id
AND t.tag IN ( 'Santa', 'Exclude' )
)
;
| PRODUCT_ID | PRODUCT_NAME |
|------------|--------------|
| 2 | Product 2 |
| 5 | Product 5 |
以下是工作演示的链接:http://sqlfiddle.com/#!2/d880d/4
修改强>
架构的示例
的礼品强>
select * from `gifts`;
| GIFT_ID | GIFT_TITLE |
|---------|------------------------|
| 1 | Red Christmas stocking |
| 2 | Santa Clause Socks |
| 3 | 40th Birthday Mug |
| 4 | Red Bowl |
<强> tags_gifts_occasion_specific 强>
select * from `tags_gifts_occasion_specific`
order by gift_id, tag_id;
| TAG_ID | GIFT_ID |
|--------|---------|
| 3 | 2 |
| 4 | 2 |
| 4 | 3 |
| 3 | 4 |
此查询获取tags_gifts_occasion_specific
的所有条目,但这些条目存在tag_id = 3
select * from `tags_gifts_occasion_specific` x
where not exists(
select 1 from `tags_gifts_occasion_specific` x1
where x.gift_id = x1.gift_id
and tag_id in ( 3 )
);
| TAG_ID | GIFT_ID |
|--------|---------|
| 4 | 3 |
现在我们使用上面的查询从gifts
表中排除一些记录:
select * from `gifts` g
where not exists(
select 1 from `tags_gifts_occasion_specific` x
where g.gift_id = x.gift_id
and not exists(
select 1 from `tags_gifts_occasion_specific` x1
where x.gift_id = x1.gift_id
and tag_id in ( 3 )
)
);
| GIFT_ID | GIFT_TITLE |
|---------|------------------------|
| 1 | Red Christmas stocking |
| 2 | Santa Clause Socks |
| 4 | Red Bowl |
| 5 | Red 40th Birthday Vase |
以下是演示的链接:http://sqlfiddle.com/#!2/558422/5