【问题标题】:SQL join filter condition, mysqlSQL连接过滤条件,mysql
【发布时间】:2012-03-14 06:02:45
【问题描述】:

我有两个看起来像这样的表(这是我实际拥有的一个示例)。

表 1:

Yr, Value
1990, 1
1990, 2
1991, 2
1992, 3

表 2:

Dte, Value2, ID
1/1/1990, 10, 1
1/2/1990, 11, 1
1/3/1990, 12, 2
1/1/1991, 20, 1
1/2/1991, 21, 2

我想先使用左连接连接两个表,然后丢弃连接集中的一些值,然后按ID 分组。我写的代码是这样的:

    select avg(Value2) v2 
     from table2 
left join table1 on (year(dte)=yr) 
    where Value>1 
 group by ID;

是先执行联接,然后where 语句中的过滤条件丢弃合并表中的行,还是先评估 where 条件,然后再评估联接?上面的例子只是为了说明,这是一个关于 SQL 如何进行操作的更普遍的问题。

【问题讨论】:

  • 它们在某种程度上是同时完成的,基本逐行操作。实际顺序可能取决于 DBMS 的优化器 - 有时执行 where first 以减少实际需要连接的行数是有意义的。在其他情况下,先加入然后执行 where 过滤器更有意义。
  • 只是一个意见,但是您可以通过自己测试轻松找到这种东西。运行带有和不带有 WHERE 子句的查询并比较结果。
  • @MarcB 问题是关于mysql的优化。
  • 我很抱歉,因为我认为我不清楚:我对优化不感兴趣,而是对评估顺序感兴趣。我需要先加入,我想知道如何做到这一点。
  • 我不具体了解 MySQL,但通常我相信大多数 RDBMS DO NOT 保证订单,因为这可能会限制语句的优化。无论如何最好不要依赖这个。你想要完成什么,你需要JOIN'首先执行'?或者,也可以将WHERE 子句中的条件放入JOIN 中(……嘿,值得一试)。

标签: mysql sql join filter where-clause


【解决方案1】:

这取决于表格的排列顺序和wheres 的顺序。在这种情况下, where 会在之后执行。因此以相反的顺序声明表会更有效,因为您有 table1 的 where 子句。

按照您的操作方式,table1 中的所有行都使用 on-clause 与 table2 中的行连接以缩小范围。然后,最后,where 子句用于连接的结果。然而,像这样:

   select avg(Value2) v2 
     from table1 
left join table2 on (year(dte)=yr) 
    where Value>1 
 group by ID;

where 子句首先在 table1 上执行,然后使用 on 子句执行连接。这是在已经缩减的 table1 版本上完成的,因此效率更高。

【讨论】:

  • 有趣:我实际上希望 MySQL 先进行连接。在上面的示例中,这无关紧要,但对于我正在做的更大的事情,我实际上需要它先进行连接,然后删除行。有什么方法可以确保这一点?你提到这是桌子的顺序……你怎么知道的?
  • @Alex 请注意,表的顺序相对于 where 子句的顺序决定了这一点。一位高级程序员在我做的一项 mysql 特定工作中教了我这个。
  • 您能详细说明一下吗?这是否意味着 where 子句在它之前的表上起作用?请解释
  • @Alex 教我的方式,第一个 where 子句尽快执行,然后第二个尽快执行,依此类推。您的 where 子句引用 table1,因此在您的原始查询中,直到连接之后才能执行该 where 子句。
猜你喜欢
  • 1970-01-01
  • 2013-01-19
  • 1970-01-01
  • 2010-11-26
  • 1970-01-01
  • 2022-10-12
  • 2016-07-14
  • 1970-01-01
  • 2015-09-20
相关资源
最近更新 更多