今天同事问我一个SQL,使用的是exists子查询,因为对SQL不是很熟,所以就趁机查了下资料,了解一下SQL中的exists和not exists的用法。
注:本文基本上是转自别人的博客,下面附上所转原文的链接:
http://www.cnblogs.com/netserver/archive/2008/12/25/1362615.html
下面是转载加个人总结:
1. 引言:
比如在Northwind数据库中有一个查询为
SELECT c.CustomerId, CompanyName FROM Customers c WHERE EXISTS( SELECT OrderID FROM Orders o WHERE o.CustomerID=c.CustomerID )
这里面的EXISTS是如何运作呢?子查询返回的是OrderId字段,可是外面的查询要找的是CustomerID和CompanyName字段,这两个字段肯定不在OrderID里面啊,这是如何匹配的呢?
2. 概括:
exists是用于检查子查询中是否至少会返回一行数据,意即exists后面的那个sql语句是否有结果返回;但要注意的是exists+这个子查询并不会返回任何数据,而只是一个boolean值:true/false。对于exists,如果exists后面的子查询中有至少一行数据,那么该子查询将返回true;如果一行数据也没有,则返回false。(not exists与之相反,如果查询结果为null,则返回true,否则返回false)
3. 语法
语法: EXISTS subquery
参数: subquery 是一个受限的 SELECT 语句 (不允许有 COMPUTE 子句和 INTO 关键字)。
结果类型: Boolean 如果子查询包含行,则返回 TRUE ,否则返回 FLASE
(二). 比较使用 EXISTS 和 IN 的查询。注意两个查询返回相同的结果。
select * from TableIn where exists(select BID from TableEx where BNAME=TableIn.ANAME)
select * from TableIn where ANAME in(select BNAME from TableEx)
注:
他们的区别之一就是in前面只能是一个字段,如ANAME in (结果集); 而exists前面可以有很多。
另外一点很重要即exists可以使用索引,而in不能(这一点还没有深入研究)。
(三). 比较使用 EXISTS 和 = ANY 的查询。注意两个查询返回相同的结果。
select * from TableIn where exists(select BID from TableEx where BNAME=TableIn.ANAME)
select * from TableIn where ANAME=ANY(select BNAME from TableEx)
NOT EXISTS 的作用与 EXISTS 正好相反。如果子查询没有返回行,则满足了 NOT EXISTS 中的 WHERE 子句, 即结果返回true。
结论:
EXISTS(包括 NOT EXISTS )子句的返回值是一个BOOL值。 EXISTS内部有一个子查询语句(SELECT ... FROM...), 我将其称为EXIST的内查询语句。其内查询语句返回一个结果集。 EXISTS子句根据其内查询语句的结果集空或者非空,返回一个布尔值。
一种通俗的可以理解为:将外查询表的每一行,代入内查询作为检验,如果内查询返回的结果取非空值,则EXISTS子句返回TRUE; 这一行行可作为外查询的结果行,否则不能作为结果。
分析器会先看语句的第一个词,当它发现第一个词是SELECT关键字的时候,它会跳到FROM关键字,然后通过FROM关键字找到表名并把表装入内存。接着是找WHERE关键字,如果找不到则返回到SELECT找字段解析,如果找到WHERE,则分析其中的条件,完成后再回到SELECT分析字段。最后形成一张我们要的虚表。
WHERE关键字后面的是条件表达式。条件表达式计算完成后,会有一个返回值,即非0或0,非0即为真(true),0即为假(false)。同理WHERE后面的条件也有一个返回值,真或假,来确定接下来执不执行SELECT。
分析器先找到关键字SELECT,然后跳到FROM关键字将STUDENT表导入内存,并通过指针找到第一条记录,接着找到WHERE关键字计算它的条件表达式,如果为真那么把这条记录装到一个虚表当中,指针再指向下一条记录。如果为假那么指针直接指向下一条记录,而不进行其它操作。一直检索完整个表,并把检索出来的虚拟表返回给用户。EXISTS是条件表达式的一部分,它也有一个返回值(true或false)。
在插入记录前,需要检查这条记录是否已经存在,只有当记录不存在时才执行插入操作,可以通过使用 EXISTS 条件句防止插入重复记录。
INSERT INTO TableIn (ANAME,ASEX)
SELECT top 1 '张三', '男' FROM TableIn
WHERE not exists (select * from TableIn where TableIn.AID = 7)
EXISTS与IN的使用效率的问题,通常情况下采用exists要比in效率高,因为IN不走索引,但要看实际情况具体使用。
IN适合于外表大而内表小的情况;EXISTS适合于外表小而内表大的情况。(因为如果表很大的情况下可能会考虑使用索引,前面说过,in是不能使用索引的)
引自其他博文:
in 是把外表和内表作hash 连接,而exists是对外表作loop循环,每次loop循环再对内表进行查询。
如果查询的两个表大小相当,那么用in和exists差别不大。
如果两个表中一个较小,一个是大表,则子查询表大的用exists,子查询表小的用in:
例如:表A(小表),表B(大表)
1:
select * from A where cc in (select cc from B)
效率低,用到了A表上cc列的索引;
select * from A where exists(select cc from B where cc=A.cc)
效率高,用到了B表上cc列的索引。
相反的
2:
select * from B where cc in (select cc from A)
效率高,用到了B表上cc列的索引;
select * from B where exists(select cc from A where cc=B.cc)
效率低,用到了A表上cc列的索引。
以上是目前的内容,如有不正确的地方,欢迎批评指正,谢谢!
注:日后可能会有更深的认识。
相关推荐
EXISTS关键字在SQL编程中扮演着至关重要的角色,它主要用于判断一个子查询是否能够返回结果集,即子查询是否为空集。当子查询返回至少一行数据时,EXISTS表达式的结果为真(TRUE),反之则为假(FALSE)。虽然EXISTS...
- **EXISTS**:用于检查子查询是否至少返回一行记录,是SQL中的一个重要逻辑关键字。 - **EXPLAIN**:用于分析和显示查询计划,帮助优化查询性能,虽然在SQL标准中未提及,但在实际应用中非常常见。 #### F系列...
在SQL数据库查询语言中,与除法运算相对应的是一种特殊的子查询,即使用exists关键字的子查询。这篇文档探讨了如何通过对比教学法,将关系代数中的除法运算与SQL中的exists子查询相结合,帮助学生更深入地理解这两种...
- **子查询限制**:`EXISTS`后的子查询只能是一个受限的`SELECT`语句,这意味着子查询中不能包含`COMPUTE`子句和`INTO`关键字。这是因为`EXISTS`只需要确定是否存在符合条件的数据,而不关心具体的数据是什么。 - *...
在SQL查询中,`EXISTS`与`NOT EXISTS`是非常实用的子查询操作符,它们主要用于检测是否存在满足一定条件的数据行。相较于`IN`、`NOT IN`等操作,`EXISTS`与`NOT EXISTS`具有更高的效率,尤其是在处理大型数据集时。 ...
10. **统一SQL大小写**:保持SQL关键字的一致性,如全部大写或全部小写,有助于提高解析效率。 当面对查询速度慢的问题时,可以采取以下措施进行优化: 1. **创建索引**:为WHERE子句、ORDER BY、DISTINCT后面经常...
在 SQL Server 2005 中,`EXISTS` 是一个非常实用的子句,用于检查子查询是否返回至少一行数据。如果子查询返回至少一行数据,则 `EXISTS` 返回 TRUE;反之则返回 FALSE。`EXISTS` 子句通常用于提高查询性能,特别是...
在SQL查询中,`EXISTS`和`NOT EXISTS`是两个非常重要的子查询操作符,它们主要用于判断子查询是否返回结果。本篇文章将详细介绍这两个关键字的用法,并通过实例进行解析。 首先,`EXISTS`的语法是:主查询中的条件...
存在量词在SQL语句中的应用是指使用Exists关键字来执行特定的查询操作。Exists用于子查询中,其主要作用是检查子查询是否至少返回一行结果。如果子查询返回结果,则Exists的结果为真(True),否则为假(False)。...
总结来说,EXISTS关键字是数据库查询中非常重要的工具,尤其在涉及复杂的逻辑判断时。通过上述案例,我们了解到EXISTS能够在多种不同的场合下使用,包括判断记录的存在性、确保数据满足特定的条件等。在实际应用中,...
在SQL中,`EXISTS` 是一个非常重要的子句,用于判断子查询是否能返回至少一行数据。这个关键字不关心子查询返回的具体数据,而仅仅关注是否有数据存在。`EXISTS` 子句通常与 `WHERE` 子句一起使用,以过滤满足特定...
23. **存储过程结构**: SQLServer 存储过程中的 `AS` 关键字在 MySQL 中需要替换为 `BEGIN...END` 结构。 24. **字符串拼接**: SQLServer 中使用加号 `+` 进行字符串拼接,而 MySQL 中使用 `concat()` 函数。 25. **...
在SQL语言中,嵌套查询是一种非常强大的工具,它允许在一个查询内部嵌入另一个查询,以实现更复杂的逻辑和数据筛选。以下将详细介绍标题和描述中提到的几个嵌套查询的例子,以及它们所代表的知识点。 1. **子查询...
EXISTS关键字用于判断一个子查询是否存在记录,EXISTS关键字通常用于WHERE子句中。 知识点14:MAX函数 MAX函数用于返回一个字段的最大值,MAX函数通常用于聚合函数中。 知识点15:GROUP BY子句 GROUP BY子句...
EXISTS关键字用于指定子查询的存在性,而IN关键字用于指定子查询的成员关系。 三、派生表查询 派生表查询是多表查询中的一种复杂查询方式。它通过在FROM子句中指定一个派生表,从而将多个表连接起来。派生表查询的...
SQL语言中,AS关键字用于为表或列指定别名,以便于查询和简化语句。在本文中,我们将总结一些常用的SQL语句,并解释AS用法的细节。 一、DELETE语句 DELETE语句用于删除表中的记录。例如,以下语句删除table1中id列...
在SQL EXISTS 语法中,主查询通常包含一个FROM子句,指定要检查的表,而WHERE子句后面跟着EXISTS关键字,接着是一个子查询。子查询本身也可以包含一个或多个条件,用于确定哪些记录符合要求。以下是一个基本的EXISTS...
在Oracle数据库中,"IN"和"EXISTS"都是用于查询某个集合的元素是否存在于另一个集合中的关键字。然而,它们在处理数据时的效率和适用场景有所不同,这主要取决于涉及的数据量以及表之间的关联。 首先,让我们来看看...
- **背景**:Hive不支持标准SQL中的`IN`和`EXISTS`关键字,但可以通过`LEFT SEMI JOIN`来模拟这些功能。 - **示例**:标准SQL中的`IN`关键字查询如下: ```sql SELECT a.key, a.value FROM a WHERE a.key IN ...