我解决了查询at this link
您能否返回未命名为“ Willow Rosenberg”且不在“如何与母亲见面”中的角色和电视节目列表?
具有以下代码:
SELECT ch.name,sh.name
FROM character ch
INNER JOIN character_tv_show chat
ON ch.id = chat.character_id
INNER JOIN tv_show sh
ON chat.tv_show_id=sh.id
WHERE ch.name != "Willow Rosenberg" AND sh.name !="How I Met Your Mother"
;
但是,我的第一次尝试是:
SELECT ch.name,sh.name
FROM character ch
WHERE ch.name != "Willow Rosenberg" /*This here*/
INNER JOIN character_tv_show chat
ON ch.id = chat.character_id
INNER JOIN tv_show sh
ON chat.tv_show_id=sh.id
WHERE sh.name !="How I Met Your Mother"
;
因为我认为以这种方式在执行联接之前只对表character
进行了过滤,因此,它的计算量减少了。
这有意义吗?
在连接多个表时,是否有一种方法可以“拆分” WHERE
子句?
答案 0 :(得分:1)
您可以使用子查询
SELECT ch.name,sh.name
FROM (
SELECT ch.name
FROM character ch
WHERE ch.name != "Willow Rosenberg") ch
INNER JOIN character_tv_show chat
ON ch.id = chat.character_id
INNER JOIN tv_show sh
ON chat.tv_show_id=sh.id
WHERE sh.name !="How I Met Your Mother"
但是我认为这没有道理。子查询将使临时表。 第一次查询将由数据库服务器优化,并且可能仅从字符表中选择需要的行
答案 1 :(得分:1)
将JOIN
视为两个表的叉积,并使用ON
子句中指定的条件对其进行过滤。然后将您的WHERE
子句应用于结果集,而不应用于参与联接的单个表。
如果仅要将WHERE
应用于连接的表之一,则必须使用子查询。然后,该子查询的过滤结果将被视为普通表,并再次使用JOIN
与 real 表联接。
如果您这样做是为了提高性能,请记住,对于正确索引的表,与子查询相比,标准JOIN
上的联接几乎总是更快。您会发现,除极少数情况外,使用JOIN的查询将比使用子查询的查询快几个数量级。
答案 2 :(得分:1)
JOIN
和WHERE
子句不一定按照您编写它们的顺序执行。通常,查询优化器会重新安排事情以使其尽可能高效(或至少认为最有效的事情),因此添加第二个WHERE
子句与添加另一个{{1 }}条件(这就是为什么不允许这样做的原因)。
您的想法还不错,但这不是数据库的实际工作方式。
答案 3 :(得分:1)
一个SELECT
只能有1个WHERE
子句。
它是在JOIN之后的。
但是您可以在加入的子查询中包含其他WHERE子句。
有时,您添加到WHERE子句中的条件可以移至JOIN的ON。
例如,以下查询将返回相同的结果
SELECT *
FROM Table1 AS t1
JOIN Table2 AS t2 ON t2.ID = t1.table2ID
WHERE t1.Col1 = 'foo'
AND t2.Col1 = 'bar'
SELECT *
FROM
(
SELECT *
FROM Table1
WHERE Col1 = 'foo'
) AS t1
JOIN Table2 AS t2 ON t2.ID = t1.table2ID
WHERE t2.Col1 = 'bar'
SELECT *
FROM Table1 AS t1
JOIN Table2 AS t2 ON (t2.ID = t1.table2ID AND t2.Col1 = 'bar')
WHERE t1.Col1 = 'foo'