SQLjoinVS SQL子查询(性能)?

我想知道如果我有一个这样的联接查询 –

Select E.Id,E.Name from Employee E join Dept D on E.DeptId=D.Id 

和一个像这样的子查询

 Select E.Id,E.Name from Employee Where DeptId in (Select Id from Dept) 

当我考虑性能哪两个查询会更快, 为什么

还有一段时间,我应该比另一个更喜欢?

对不起,如果这太微不足道了,但我很困惑。 另外,如果你们可以build议我使用工具来衡量两个查询的性能,那将是非常好的。 非常感谢!

我会预计第一个查询更快,主要是因为你有一个等价的和明确的JOIN。 根据我的经验, IN是一个非常慢的操作符,因为SQL通常将其评估为由“OR”( WHERE x=Y OR x=Z OR... )分隔的一系列WHERE子句。

和所有的SQL一样,你的里程可能会有所不同。 速度将取决于很多的索引(你是否有ID列的索引?这将有助于很多…)等等。

唯一真正以100%确定性告诉的方法是打开性能跟踪(IO统计特别有用)并运行它们。 确保在运行之间清除caching!

那么,我相信这是一个“古老而又金”的问题。 答案是:“这取决于!”。 演出是一个非常微妙的主题,所以说:“永远不要使用子查询,总是join”。 在下面的链接中,您会发现一些基本的最佳实践,我发现这些实践非常有帮助: Here 1 Here 2 Here 3

我有一张有50000个元素的桌子,结果我在找的是739个元素。

我的查询起初是这样的:

 SELECT p.id, p.fixedId, p.azienda_id, p.categoria_id, p.linea, p.tipo, p.nome FROM prodotto p WHERE p.azienda_id = 2699 AND p.anno = ( SELECT MAX(p2.anno) FROM prodotto p2 WHERE p2.fixedId = p.fixedId ) 

而且花了7.9s来执行。

我的查询在最后是这样的:

 SELECT p.id, p.fixedId, p.azienda_id, p.categoria_id, p.linea, p.tipo, p.nome FROM prodotto p WHERE p.azienda_id = 2699 AND (p.fixedId, p.anno) IN ( SELECT p2.fixedId, MAX(p2.anno) FROM prodotto p2 WHERE p.azienda_id = p2.azienda_id GROUP BY p2.fixedId ) 

花了0.0256s

良好的SQL,很好。

开始查看执行计划,以查看SQl服务器如何解释它们的差异。 您还可以使用Profiler实际运行多次查询并获取差异。

我不希望这些是如此可怕的不同,在使用联接而不是子查询的情况下,使用相关子查询时,可以获得真正的大性能收益。

EXISTS往往比这两者中的任何一个都好,而当你正在谈论左连接,你想要所有logging不在左连接表中,那么NOT EXISTS通常是更好的select。

性能是基于您正在执行的数据量…

如果是20k左右的数据较less。 JOIN工作得更好。

如果数据更像100k +那么IN的效果更好。

如果你不需要其他表中的数据,IN是好的,但是去EXISTS更好。

我testing的所有这些标准和表都有适当的索引。

表演应该是一样的; 在表格上应用正确的索引和集群(在这个主题上有一些很好的资源 )是非常重要的。

(编辑以反映更新的问题)

这两个查询在语义上可能不相同。 如果一个员工为多个部门工作(可能在我工作的企业中;诚然,这意味着您的表没有完全标准化),那么第一个查询将返回重复的行,而第二个查询则不会。 为了在这种情况下使查询等效,必须将DISTINCT关键字添加到SELECT子句中,这可能会影响性能。

请注意,有一个devise经验法则规定一个表应该模拟实体/类或实体/类之间的关系,但不能同时build模。 因此,我build议你创build第三个表格,比如OrgChart ,来模拟员工和部门之间的关系。

您可以使用解释计划来获得客观的答案。

对于你的问题, 一个Existsfilter可能会执行得最快。

最后一个查询在相关的子查询中包含了azienda_id,但是最初的查询并没有在相关的子查询中包含azienda_id。 所以比较是不一样的。

通过比较“使用客户统计”的数量,我testing了HLGEM的理论,结果表明不存在的是比左边的连接快,当search所有logging不在左边的表。

SQL的美妙之处在于它的写作方式很多,性能并不完全取决于连接或子查询,而是您正在寻找的结果集。