2013-02-16 53 views
3

我正在刷新我的SQL。
我正在阅读有关子查询以及使用相关子查询引用外部的可能性。
例子:子查询和外部引用相关子查询的可能性

SELECT * 
FROM ORDERS O 
WHERE 'ROAD BIKE' = 
(SELECT DESCRIPTION FROM PART P WHERE P.PARTNUM = O.PARTNUM) 

这相当于一个连接:

SELECT O.ORDEREDON, O.NAME, 
O.PARTNUM, O.QUANTITY, O.REMARKS 
FROM ORDERS O, PART P 
WHERE P.PARTNUM = O.PARTNUM AND P.DESCRIPTION = 'ROAD BIKE' 

我的问题是,我没有得到第一种形式,当/为什么我们使用它。何时外部引用的查询有用?

+0

我想你可以说前者更清晰。 – 2013-02-16 21:05:33

+0

你也可以说前者要慢得多,直到SQL 6.0 – Achrome 2013-02-16 21:06:06

+0

@ExplosionPills:为什么它更清晰?我甚至都不知道这些查询是如何工作的以及在哪里应用它们。 – Cratylus 2013-02-16 21:06:53

回答

2

订单有专门的部件号的引用,使Orders表的外键的部件编号。

我们希望所有的零件编号是“公路自行车”的订单。

第一种形式首先做一个子查询的每个记录,以检查是否O.PARTNUM是“公路自行车”零件号。

想它的方式是,主查询正在经历Orders表中的每个记录。在每条记录上,它执行一个子查询,在查询中使用PARTNUM字段。因此,如果您在子查询中使用订单记录的PARTNUM,请选择PARTNUM表中的PARTNUM记录,然后选择DESCRIPTION字段。然后,主要查询的where子句检查“Road Bike”是否等于从子查询返回的描述。

我会建议不要使用第一种形式,因为它是一个相关的查询,你应该避免出于性能方面的相关查询,因此使用第二种形式。第一种形式的更好的版本是:

SELECT * 
FROM ORDERS O 
WHERE O.PARTNUM = 
(SELECT P.PARTNUM FROM PART P WHERE DESCRIPTION = 'ROAD BIKE') 

这不是相关的查询。数据库可以执行一次子查询,以“ROAD BIKE”为描述获取记录的PARTNUM,然后使用条件WHERE O.PARTNUM等于子查询的结果运行主查询。

+0

是否有一个用例相关的子查询是唯一的出路?解决一些具体问题? – Cratylus 2013-02-16 21:35:31

+0

这些是一些相关的子查询,没有其他等效的SQL而没有相关的子查询。那么这是不可避免的。 – 2013-02-16 21:36:46

+0

我的意思是说,它不是SQL,每天都会写出让我们说。这是一个角落案例? – Cratylus 2013-02-16 21:37:45

2

总之,你应该避免像瘟疫这样的相关子查询。

相关子查询对外部表中的每一行执行一次内部查询。这将导致可怕的表现(1万行的外部表将导致执行100万次内部查询!)

,另一方面联接是非常有效和数据库是在优化他们非常好。

如果可能,请始终将查询表达为优先于相关子查询的连接。

+0

1)是否有一个使用案例,相关的子查询是唯一的出路? 2)一般情况下,连接和相关子查询或连接和子查询之间的性能差异是什么? – Cratylus 2013-02-16 21:34:57

+0

相关的子查询将使MySQL 6.0复出。 – Achrome 2013-02-16 21:39:49

+0

@AshwinMukhija:不确定你的意思。我在MySQL中运行第一个表单(这是一个相关的子查询),它的工作原理 – Cratylus 2013-02-16 21:57:59

0

这样一个场景,一个子查询可能是合适的是这样的:

select some fields 
from some tables 
where some conditions are met 
and somefield = (select min(something) from etc) 

不过,我不知道这是相关子查询。语义学不是我的强项。

+0

相关的子查询是当你的子查询引用你的外部查询的一部分。在我的例子中注意'WHERE P.PARTNUM = O.PARTNUM'。表'O'被定义在*之外。 – Cratylus 2013-02-16 22:23:48