关于 “A LEFT JOIN B ON 条件表达式” 的一点提醒

ON 条件(“A LEFT JOIN B ON 条件表达式”中的ON)用来决定如何从 B 表中检索数据行,即使on中包含有A表中的列的限制条件,也不会过滤A的任何数据(A的数据只会通过where过滤)。

如果 B 表中没有任何一行数据匹配 ON 的条件,将会额外生成一行所有列为 NULL 的数据

在匹配阶段 WHERE 子句的条件都不会被使用。仅在匹配阶段完成以后,WHERE 子句条件才会被使用。它将从匹配阶段产生的数据中检索过滤。

让我们看一个 LFET JOIN 示例:

01 mysql> CREATE TABLE `product` (
02   `id` int(10) unsigned NOT NULL auto_increment,
03   `amount` int(10) unsigned default NULL,
04   PRIMARY KEY  (`id`)
05 ) ENGINE=MyISAM AUTO_INCREMENT=5 DEFAULT CHARSET=latin1
06   
07 mysql> CREATE TABLE `product_details` (
08   `id` int(10) unsigned NOT NULL,
09   `weight` int(10) unsigned default NULL,
10   `exist` int(10) unsigned default NULL,
11   PRIMARY KEY  (`id`)
12 ) ENGINE=MyISAM DEFAULT CHARSET=latin1
13   
14 mysql> INSERT INTO product (id,amount)
15        VALUES (1,100),(2,200),(3,300),(4,400);
16 Query OK, 4 rows affected (0.00 sec)
17 Records: 4  Duplicates: 0  Warnings: 0
18   
19 mysql> INSERT INTO product_details (id,weight,exist)
20        VALUES (2,22,0),(4,44,1),(5,55,0),(6,66,1);
21 Query OK, 4 rows affected (0.00 sec)
22 Records: 4  Duplicates: 0  Warnings: 0
23   
24 mysql> SELECT FROM product;
25 +----+--------+
26 | id | amount |
27 +----+--------+
28 |  1 |    100 |
29 |  2 |    200 |
30 |  3 |    300 |
31 |  4 |    400 |
32 +----+--------+
33 rows in set (0.00 sec)
34   
35 mysql> SELECT FROM product_details;
36 +----+--------+-------+
37 | id | weight | exist |
38 +----+--------+-------+
39 |  2 |     22 |     0 |
40 |  4 |     44 |     1 |
41 |  5 |     55 |     0 |
42 |  6 |     66 |     1 |
43 +----+--------+-------+
44 rows in set (0.00 sec)
45   
46 mysql> SELECT FROM product LEFT JOIN product_details
47        ON (product.id = product_details.id);
48 +----+--------+------+--------+-------+
49 | id | amount | id   | weight | exist |
50 +----+--------+------+--------+-------+
51 |  1 |    100 | NULL |   NULL |  NULL |
52 |  2 |    200 |    2 |     22 |     0 |
53 |  3 |    300 | NULL |   NULL |  NULL |
54 |  4 |    400 |    4 |     44 |     1 |
55 +----+--------+------+--------+-------+
56 rows in set (0.00 sec)

ON 子句和 WHERE 子句有什么不同?

一个问题:下面两个查询的结果集有什么不同么?

1 1. SELECT FROM product LEFT JOIN product_details
2          ON (product.id = product_details.id)
3          AND   product_details.id=2;
4 2. SELECT FROM product LEFT JOIN product_details
5          ON (product.id = product_details.id)
6          WHERE product_details.id=2;

用例子来理解最好不过了:

01 mysql> SELECT FROM product LEFT JOIN product_details
02        ON (product.id = product_details.id)
03        AND product_details.id=2;
04 +----+--------+------+--------+-------+
05 | id | amount | id   | weight | exist |
06 +----+--------+------+--------+-------+
07 |  1 |    100 | NULL |   NULL |  NULL |
08 |  2 |    200 |    2 |     22 |     0 |
09 |  3 |    300 | NULL |   NULL |  NULL |
10 |  4 |    400 | NULL |   NULL |  NULL |
11 +----+--------+------+--------+-------+
12 rows in set (0.00 sec)
13   
14 mysql> SELECT FROM product LEFT JOIN product_details
15        ON (product.id = product_details.id)
16        WHERE product_details.id=2;
17 +----+--------+----+--------+-------+
18 | id | amount | id | weight | exist |
19 +----+--------+----+--------+-------+
20 |  2 |    200 |  2 |     22 |     0 |
21 +----+--------+----+--------+-------+
22 1 row in set (0.01 sec)

第一条查询使用 ON 条件决定了从 LEFT JOIN的 product_details表中检索符合的所有数据行。

第二条查询做了简单的LEFT JOIN,然后使用 WHERE 子句从 LEFT JOIN的数据中过滤掉不符合条件的数据行。

再来看一些示例:

01 mysql>
02 mysql> SELECT FROM product LEFT JOIN product_details
03        ON product.id = product_details.id
04        AND product.amount=100;
05 +----+--------+------+--------+-------+
06 | id | amount | id   | weight | exist |
07 +----+--------+------+--------+-------+
08 |  1 |    100 | NULL |   NULL |  NULL |
09 |  2 |    200 | NULL |   NULL |  NULL |
10 |  3 |    300 | NULL |   NULL |  NULL |
11 |  4 |    400 | NULL |   NULL |  NULL |
12 +----+--------+------+--------+-------+
13 rows in set (0.00 sec)

所有来自product表的数据行都被检索到了,但没有在product_details表中匹配到记录(product.id = product_details.id AND product.amount=100 条件并没有匹配到任何数据)

01 mysql> SELECT FROM product LEFT JOIN product_details
02        ON (product.id = product_details.id)
03        AND product.amount=200;
04 +----+--------+------+--------+-------+
05 | id | amount | id   | weight | exist |
06 +----+--------+------+--------+-------+
07 |  1 |    100 | NULL |   NULL |  NULL |
08 |  2 |    200 |    2 |     22 |     0 |
09 |  3 |    300 | NULL |   NULL |  NULL |
10 |  4 |    400 | NULL |   NULL |  NULL |
11 +----+--------+------+--------+-------+
12 rows in set (0.01 sec)

同样,所有来自product表的数据行都被检索到了,有一条数据匹配到了。

原文地址:http://blog.csdn.net/longyulu/article/details/7924833

MySQL的left join中on与where的区别的更多相关文章

  1. MySQL之LEFT JOIN中使用ON和WHRERE对表数据

    背景 left join在我们使用mysql查询的过程中可谓非常常见,比如博客里一篇文章有多少条评论.商城里一个货物有多少评论.一条评论有多少个赞等等.但是由于对join.on.where等关键字的不 ...

  2. left join中where与on的区别

    举例进行说明,我们现在有两个表,即商品表(products)与sales_detail(销售记录表).我们主要是通过这两个表来对MySQL关联left join 条件on与where 条件的不同之处进 ...

  3. SQL JOIN 中 on 与 where 的区别

    left join : 左连接,返回左表中所有的记录以及右表中连接字段相等的记录. right join : 右连接,返回右表中所有的记录以及左表中连接字段相等的记录. inner join : 内连 ...

  4. 关联查询left join中on 和where 的区别

    关于 “A LEFT JOIN B ON 条件表达式” 的一点提醒 ON 条件(“A LEFT JOIN B ON 条件表达式”中的ON)用来决定如何从 B 表中检索数据行. 如果 B 表中没有任何一 ...

  5. 深入Oracle的left join中on和where的区别详解

    -- from http://blog.itpub.net/30175262/viewspace-1472060/ 今天遇到一个求某月所有天数的统计结果,如果某日的结果是0也需要显示出来,即: 日期 ...

  6. mysql中left join中的on条件 和 where条件区别

    需要知道sql中关键字的执行顺序. FROM-> ON->JOIN-> WHERE->GROUP BY-> HAVING->SELECT-> DISTINCT ...

  7. mysql left join中where和on条件的区别

    left join中关于where和on条件的几个知识点: 1.多表left join是会生成一张临时表,并返回给用户 2.where条件是针对最后生成的这张临时表进行过滤,过滤掉不符合where条件 ...

  8. mysql left join中on后加条件判断和where中加条件的区别

    left join中关于where和on条件的几个知识点: .多表left join是会生成一张临时表,并返回给用户 .where条件是针对最后生成的这张临时表进行过滤,过滤掉不符合where条件的记 ...

  9. 转: 从Mysql某一表中随机读取n条数据的SQL查询语句

    若要在i ≤ R ≤ j 这个范围得到一个随机整数R ,需要用到表达式 FLOOR(i + RAND() * (j – i + 1)).例如, 若要在7 到 12 的范围(包括7和12)内得到一个随机 ...

随机推荐

  1. Java6 String.substring()方法的内存泄露

    substring(start,end)在Java编程里面经常使用,没想到如果使用不当,会出现内存泄露. 要了解substring(),最好的方法便是查看源码(jdk6): /** * <blo ...

  2. Easyui Combotree问题及其相关

    Easyui的setValue方法无效 今天在开发项目的时候,遇到第一个很奇怪的问题:EasyUI的setValue方法无效. $('#department_parent').combotree('s ...

  3. 20135220谈愈敏Blog7_可执行程序的装载

    可执行程序的装载 谈愈敏 原创作品转载请注明出处 <Linux内核分析>MOOC课程 http://mooc.study.163.com/course/USTC-1000029000 一. ...

  4. scrollview中套listView的问题,记录一下。

    开发一个订单详情界面,详情界面上面要显示收货地址.订单总金额等,中间部分要一个listView,下面还有一些东西 但是一个界面显示不全,肯定要scrollview,然后发现listView竟然只显示第 ...

  5. MVC4/5+jquery+bootstrap样式+dataTables+linq+WCF+EF6后台和前台的框架集合!好蛋疼哦!数据库支持MYSQL 和MSSQL,oracle。集成腾讯企业邮箱收邮件同步用户SSO登陆等功能。

    花费了我好多心血,才做出来,下个项目准备用这个框架! 大家有没有做这方面的可以交流一下! 花费了我好多心血,才做出来,下个项目准备用这个框架! 大家有没有做这方面的可以交流一下! 花费了我好多心血,才 ...

  6. EntityFramework系列:Repository模式与单元测试

    1.依赖IRepository接口而不是直接使用EntityFramework 使用IRepository不只是架构上解耦的需要,更重要的意义在于Service的单元测试,Repository模式本身 ...

  7. 一种仿照Asp.net Mvc思维构建WebSocket服务器的方法

    问题场景 Asp.net Mvc提供了DependencyResolver.Routing.Filter. Modelbinder等webForm所没有新概念,提高Web服务编写的便利性,记得很久之前 ...

  8. javascript基于原型实现面向对象

    传统的OO语言有类的概念,但js(ES5)却是基于原型实现的面向对象. 原型是?我们创建的每一个函数都会有一个原型(prototype)属性,这个属性是一个指针,指向函数的原型(prototype)对 ...

  9. Spring学习(三)——Spring中的依赖注入的方式

    [前面的话] Spring对我太重要了,做个关于web相关的项目都要使用Spring,每次去看Spring相关的知识,总是感觉一知半解,没有很好的系统去学习一下,现在抽点时间学习一下Spring.不知 ...

  10. Linq之Lambda表达式初步认识

    目录 写在前面 匿名方法 一个例子 Lambda 定义 一个例子 总结 参考文章 写在前面 元旦三天在家闲着无事,就看了看Linq的相关内容,也准备系统的学习一下,作为学习Linq的前奏,还是先得说说 ...