ql语句中left join和inner join中的on与where的区别分析
sql语句中left join和inner join中的on与where的区别分析
关于SQL SERVER的表联接查询INNER JOIN 、LEFT JOIN和RIGHT JOIN,经常会用到ON和WHERE的条件查询,以前用的时候有时是凭感觉的,总是没有搞清楚,今日亲自测试了下,理解到了一些内容,在此分享。
要测试,首先我们来创建三张表,数据库就根据自己的情况而定
创建表TestJoinOnOrWhere_A、TestJoinOnOrWhere_B、TestJoinOnOrWhere_C

/****** Object: Table [dbo].[TestJoinOnOrWhere_A] Script Date: 2015/4/3 14:34:41 ******/
CREATE TABLE [dbo].[TestJoinOnOrWhere_A](
[id] [int] NULL,
[value] [int] NULL
) ON [PRIMARY] GO
/****** Object: Table [dbo].[TestJoinOnOrWhere_B] Script Date: 2015/4/3 14:34:41 ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[TestJoinOnOrWhere_B](
[id] [int] NULL,
[value] [int] NULL
) ON [PRIMARY] GO
/****** Object: Table [dbo].[TestJoinOnOrWhere_C] Script Date: 2015/4/3 14:34:41 ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
CREATE TABLE [dbo].[TestJoinOnOrWhere_C](
[id] [int] NULL,
[value] [int] NULL
) ON [PRIMARY]

表创建好了然后我们添加几条数据

INSERT [dbo].[TestJoinOnOrWhere_A] ([id], [value]) VALUES (1, 1)
INSERT [dbo].[TestJoinOnOrWhere_A] ([id], [value]) VALUES (2, 1)
INSERT [dbo].[TestJoinOnOrWhere_A] ([id], [value]) VALUES (3, 2)
INSERT [dbo].[TestJoinOnOrWhere_B] ([id], [value]) VALUES (1, 1)
INSERT [dbo].[TestJoinOnOrWhere_B] ([id], [value]) VALUES (2, 3)
INSERT [dbo].[TestJoinOnOrWhere_B] ([id], [value]) VALUES (3, 4)
INSERT [dbo].[TestJoinOnOrWhere_C] ([id], [value]) VALUES (1, 1)
INSERT [dbo].[TestJoinOnOrWhere_C] ([id], [value]) VALUES (2, 2)
INSERT [dbo].[TestJoinOnOrWhere_C] ([id], [value]) VALUES (3, 3)

现在我们开始测试
语句1:SELECT * FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id AND a.value = 1
语句2:SELECT * FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id
结果1:
id value id value
-------------------------------
1 1 1 1
2 1 2 3
3 2 NULL NULL
结果2
id value id value
-------------------------------
1 1 1 1
2 1 2 3
3 2 3 4
在网上查询到,有的人说a.value = 1没有生效,其实不然,它已经生效,只是在左联接查询时,左表的数据是不会受影响,只有右表的数据会根据a.value = 1条件取出左表(a表)Value为1的行,通过上面两个语句的结果就可以看出,那么我们用右表筛选条件会出现什么呢?看看下面语句
语句3:SELECT * FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id AND b.value = 1
结果3:
id value id value
-------------------------------
1 1 1 1
2 1 NULL NULL
3 2 NULL NULL
以上结果看出,也只是影响了右表的数据
语句4:SELECT * FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.value = 1
结果4:
id value id value
-------------------------------
1 1 1 1
1 1 2 3
1 1 3 4
2 1 1 1
2 1 2 3
2 1 3 4
3 2 NULL NULL
从上面语句结果看出,也只影响了右表的数据(取出所有a表value对应为1的b表数据)
所以在左联接查询时ON后面的条件只会影响右表,相反右联接查询影响的就是左边的表数据
如果用WHERE呢?我们看下下面的语句
语句5:SELECT * FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id where a.value = 1 语句6:SELECT * FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id where b.value = 1
结果5:
id value id value
-------------------------------
1 1 1 1
2 1 2 3
结果6:
id value id value
-------------------------------
1 1 1 1
可以从结果看出,这个影响的结果就是全部的表,就相当于通过ON条件联接查询查询的结果,然后通过WHERE后面的条件取总体筛选
对于INNER JOIN 的ON条件会怎样影响呢?先看下面语句执行结果
语句7: SELECT * FROM dbo.TestJoinOnOrWhere_A AS a INNER JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id AND a.value = 1
语句8: SELECT * FROM dbo.TestJoinOnOrWhere_A AS a INNER JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id AND b.value = 1
语句9: SELECT * FROM dbo.TestJoinOnOrWhere_A AS a INNER JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id WHERE a.value = 1
语句10:SELECT * FROM dbo.TestJoinOnOrWhere_A AS a INNER JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id WHERE b.value = 1
结果7/9:
id value id value
-------------------------------
1 1 1 1
2 1 2 3
结果8/10:
id value id value
-------------------------------
1 1 1 1
上面通过WHERE和ON查询出来的结果是一样的,由此可看出,INNER JOIN 的ON条件和WHERE条件影响的都是一个效果,影响整体的查询结果。
下面我们再来看下对于LEFT JOIN的三表查询对于WHERE和ON影响的结果
语句11:SELECT a.id AS a_id,a.value AS a_value,b.id AS b_id,b.value AS b_value,c.id AS c_id,c.value AS c_value FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id AND a.value = 1 LEFT JOIN dbo.TestJoinOnOrWhere_C AS c ON b.id = c.id
语句12:SELECT a.id AS a_id,a.value AS a_value,b.id AS b_id,b.value AS b_value,c.id AS c_id,c.value AS c_value FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id AND b.value = 1 LEFT JOIN dbo.TestJoinOnOrWhere_C AS c ON b.id = c.id
语句13:SELECT a.id AS a_id,a.value AS a_value,b.id AS b_id,b.value AS b_value,c.id AS c_id,c.value AS c_value FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id AND a.value = 1 LEFT JOIN dbo.TestJoinOnOrWhere_C AS c ON b.id = c.id AND b.value = 1
语句14:SELECT a.id AS a_id,a.value AS a_value,b.id AS b_id,b.value AS b_value,c.id AS c_id,c.value AS c_value FROM dbo.TestJoinOnOrWhere_A AS a LEFT JOIN dbo.TestJoinOnOrWhere_B AS b ON a.id = b.id AND a.value = 1 LEFT JOIN dbo.TestJoinOnOrWhere_C AS c ON b.id = c.id AND c.value = 2
结果11:
a_id a_value b_id b_value c_id c_value
-----------------------------------------------------
1 1 1 1 1 1
2 1 2 3 2 2
3 2 NULL NULL NULL NULL
结果12:
a_id a_value b_id b_value c_id c_value
-----------------------------------------------------
1 1 1 1 1 1
2 1 NULL NULL NULL NULL
3 2 NULL NULL NULL NULL
结果13:
a_id a_value b_id b_value c_id c_value
-----------------------------------------------------
1 1 1 1 1 1
2 1 2 3 NULL NULL
3 2 NULL NULL NULL NULL
结果14:
a_id a_value b_id b_value c_id c_value
-----------------------------------------------------
1 1 1 1 NULL NULL
2 1 2 3 2 2
3 2 NULL NULL NULL NULL
通过以上三表数据查询结果,可以看出,LEFT JOIN 查询,对于ON的单独表条件始终只会影响条件表的右表(如,a.value=1会影响b表关联的a表value字段值为1的行,并不会限制a表的数据只显示value=1的行),RIGHT JOIN 影响效果恰恰相反
在使用ON条件时LEFT JOIN影响的是右侧的第二张第三张表,并不会对最左侧的表影响,所以对于a,b,c,三张表,a表数据是不受ON条件影响的,只会影响联接查询后的b或c数据
而WHERE就相当于在WHERE条件之前查询的数据当着一个表,然后通过WHERE条件进行筛选数据,所以影响的是整体。
本文来自wl131710,转载请注明出处:http://www.cnblogs.com/wanglu/p/4390612.html
ql语句中left join和inner join中的on与where的区别分析的更多相关文章
- sql语句中left join、right join 以及inner join之间的使用与区别
sql语句中left join.right join 以及innerjoin之间的使用与区别 left join(左联接) 返回包括左表中的所有记录和右表中联结字段相等的记录 right join( ...
- sql中in和exist语句的区别?(补充了left join和right join)
in和exists(摘录自百度)in 是把外表和内表作hash 连接,而exists是对外表作loop循环,每次loop循环再对内表进行查询. 如果两个表中一个较小,一个是大表,则子查询表大的用exi ...
- sql语句中left join和inner join中的on与where的区别分析
关于SQL SERVER的表联接查询INNER JOIN .LEFT JOIN和RIGHT JOIN,经常会用到ON和WHERE的条件查询,以前用的时候有时是凭感觉的,总是没有搞清楚,今日亲自测试了下 ...
- SQL语句中LEFT JOIN、JOIN、INNER JOIN、RIGHT JOIN的区别?
w3school的一套sql教程: http://www.w3school.com.cn/sql/index.asp left join :左连接,返回左表中所有的记录以及右表中连接字段相等的记录.r ...
- Hive 中Join的专题---Join详解
1.什么是等值连接? 2.hive转换多表join时,如果每个表在join字句中,使用的都是同一个列,该如何处理? 3.LEFT,RIGHT,FULL OUTER连接的作用是什么? 4.LEFT或RI ...
- HIVE中join、semi join、outer join
补充说明 left outer join where is not null与left semi join的联系与区别:两者均可实现exists in操作,不同的是,前者允许右表的字段在select或 ...
- Mysql中eft join、right join、inner join的区别
left join(左联接) 返回包括左表中的所有记录和右表中联结字段相等的记录 right join(右联接) 返回包括右表中的所有记录和左表中联结字段相等的记录inner join(等值连接) 只 ...
- mysql中left join ,right join 以及inner join 比较
下面是例子分析表A记录如下: aID aNum 1 a20050111 2 a20050112 3 a20050113 4 ...
- Access SQL中Left Join、Right Join和Inner Join的使用
1.表结构 表A 表B 2.Left Join 示例:2.1 Select * From A left join B on A. ...
随机推荐
- 【高速接口-RapidIO】5、Xilinx RapidIO核例子工程源码分析
提示:本文的所有图片如果不清晰,请在浏览器的新建标签中打开或保存到本地打开 一.软件平台与硬件平台 软件平台: 操作系统:Windows 8.1 64-bit 开发套件:Vivado2015.4.2 ...
- 刺透内网的HTTP代理
从偶然出发 在做测试的时候发现了这样一个漏洞,原请求报文如下: GET / HTTP/1.1 Host: attack_website [... HEADER ...] ... 当时最初目的是想测SS ...
- PopupWindow 以及拍照、裁剪
实现这样的效果 圆角图片的自定义控件直接拷进来,和com一个等级 想要弹出内容可以使用悬浮窗 layout_pupup <LinearLayout xmlns:android="htt ...
- Kali学习笔记19:NESSUS安装及使用
Nessus 百度百科:Nessus 是目前全世界最多人使用的系统漏洞扫描与分析软件.总共有超过75,000个机构使用Nessus 作为扫描该机构电脑系统的软件. 就我而言:漏洞扫描方面最强大的工具之 ...
- 安卓视频播放器(VideoView)
VideoView是安卓自带的视频播放器类,该类集成有显示和控制两大部分,在布局文件中添加VideoView然后在java文件中简单的调用控制命令,即可实现本地或者网络视频的播放.本章实现视频的居中播 ...
- wsgiref源码解析
wsgiref是PEP 333定义的wsgi规范的范例实现,里面的功能包括了: wsgi的环境变量 应答头部的处理 实现简单的HTTP服务器 简单的对程序端和服务器端校验函数 我们先看一个简单的代码实 ...
- 全网最详细的一款满足多台电脑共用一个鼠标和键盘的工具Synergy(图文详解)
不多说,直接上干货! 前言 如今无论你是在公司做大数据开发还是实验室里搞科研,这个软件确实好用,作为正在通往大数据架构师路上的我们没有几台电脑怎么行?台式机.笔记本,都放在写字台上,笔记本内置键盘鼠标 ...
- Java 容器 & 泛型:五、HashMap 和 TreeMap的自白
Writer:BYSocket(泥沙砖瓦浆木匠) 微博:BYSocket 豆瓣:BYSocket Java 容器的文章这次应该是最后一篇了:Java 容器 系列. 今天泥瓦匠聊下 Maps. 一.Ma ...
- com.javax.servlet 慢慢看完慢慢学完
1.接口 RequestDispatcher 类说明 定义一个对象,从客户端接收请求,然后将它发给服务器的可用资源 (例如Servlet.CGI.HTML文件.JSP文件).Servlet引擎创 建r ...
- 【原创】驱动加载之OpenService
SC_HANDLE WINAPI OpenService( _In_ SC_HANDLE hSCManager, _In_ LPCTSTR lpServiceName, _In_ DWORD dwDe ...