Where 子句在联结表中没有按预期工作?

Posted

技术标签:

【中文标题】Where 子句在联结表中没有按预期工作?【英文标题】:Where clause not working as expected with junction table? 【发布时间】:2014-12-07 07:14:46 【问题描述】:

我有一个联结表,它在另外两个表之间创建多对多关系。这是图表。

这是我的基本 SQL 查询。

SELECT `tag_to_url`.url_id, `websites`.url, `tags`.tag_name 
FROM `tag_to_url` 
INNER JOIN (`websites`,`tags`) ON `websites`.url_id = `tag_to_url`.url_id 
AND `tag_to_url`.tag_id = `tags`.tag_id 
ORDER BY `tag_to_url`.url_id

这是一个示例结果。

+--------------------+-------------+
|         url        |   tag_name  |
+--------------------+-------------+
|     google.com     |    search   |
|     google.com     |    e-mail   |
| stackexchange.com  |     q&a     |
| stackexchange.com  | programming |
| stackexchange.com  |   database  |
+--------------------+-------------+

这些结果基本上是我正在寻找的结果,尽管我尝试对无法正常工作的 URL 进行分组。如果我包含一个WHERE 子句,查询也将正常工作。

...
...
WHERE `tags`.tag_name = 'database'

+--------------------+-------------+
|         url        |   tag_name  |
+--------------------+-------------+
| stackexchange.com  |   database  |
+--------------------+-------------+

但是,当我将 AND 运算符添加到 WHERE 条件时,我期待这个。

WHERE `tags`.tag_name = 'database' AND `tags`.tag_name = 'q&a'

+--------------------+-------------+
|         url        |   tag_name  |
+--------------------+-------------+
| stackexchange.com  |   database  |
| stackexchange.com  |     q&a     |
+--------------------+-------------+

但是,我得到:

mysql returned an empty result set (i.e. zero rows). (Query took 0.0027 sec)

我也尝试将ON 中的条件与JOIN 添加,但结果是一样的。请问我做错了什么?

编辑:

此查询的目的是获取一个或多个标签以及与其关联的 URL 列表。我需要能够使用多个 AND 运算符来仅检索那些特定的标签。它需要像堆栈溢出一样工作,其中有一个问题(URL)和多个附加标签。

【问题讨论】:

【参考方案1】:

您需要在 where 子句中使用 OR 而不是 AND,因为您要同时查找数据库和 q&a。

所以 where 条件应该是 WHEREtags.tag_name = 'database' OR 'q&a'

【讨论】:

谢谢,但我也试过了。它只给出带有database 标签的行。 我不确定 MySQL 但如果它类似于 SQL Server,你应该像这样使用它WHERE tags.tag_name = 'database' OR tags.tag_name = 'q&a' 检查这是否有效 我真的不知道,我已经尝试了所有我能想到的方法,并且已经研究了好几天,但它就是行不通。似乎结果与第一个 where 一起返回,它忽略了第二个。 JOIN 可能有问题,并且它们没有正确关联。 好吧,我尝试在 SQLFiddle 上解决它,它似乎可以工作你能重现你的问题here 嗯,OR 实际上是在返回一些东西,但它只返回与 database 相关的所有记录,以及与 databaseq&a 相关的记录。我需要一个查询,它只返回与databaseq&a 相关的记录,而不是单独的标签。这就是我使用AND 运算符的原因。【参考方案2】:

在mysql中使用ANDOR的正确方法是

select * from `table` where col1 = 'someval' and col2='someval' ;

select * from `table` where col1 = 'someval' OR col1='someval' ;

您需要在每个条件中指定列名。

所以你需要将查询设置为

WHERE `tags`.tag_name = 'database' OR `tags`.tag_name 'q&a'

同样的声明可以是IN

WHERE `tags`.tag_name IN('database','q&a')

编辑:这是可以使用group_concatgroup by 完成工作的查询

SELECT 
tu.url_id, 
w.url, 
group_concat(t.tag_name) as tag_name
FROM tag_to_url tu
inner join websites w on w.url_id = tu.url_id 
inner join tags t on t.tag_id = tu.tag_id
where t.tag_name in ('database','q&a')
group by w.url
having count(*) = 2

【讨论】:

这是我的错字,我已更正。仍然不返回任何行。 你正在做AND,这意味着获取tag_name 同时是databaseq&a 的行,这是不可能的。将AND 更改为ORIN 我建议使用where trim(tags.tag_name) = 'database' OR trim(tags.tag_name) = 'q&a'trim(tags.tag_name) in ('database','q&a') 这将确保如果有空格,那么在搜索之前会注意这一点。此外,在某些情况下,& 可以在数据库中保存为&,如果没有正确完成,则可以从前端保存。 是的,您可以使用group_concat(t.tag_name order by t.tag_name) 你成就了我的一周 Abhik :)

以上是关于Where 子句在联结表中没有按预期工作?的主要内容,如果未能解决你的问题,请参考以下文章

Laravel路线,其中where子句不按预期工作

联结表

MySQL group_concat 与 where 子句

All 子句核心数据谓词未按预期工作

Hive - Parquet 格式 - OR 子句在未按预期工作的地方

select count() 查询中的限制子句未按预期工作