【问题标题】:sql INNER JOIN table variable ON VS. INNER JOIN (select) ONsql INNER JOIN 表变量 ON VS。 INNER JOIN(选择)ON
【发布时间】:2011-10-11 09:42:25
【问题描述】:

我想知道使用表变量是否比使用内连接 (select) 性能更高或更低
示例:

DECLARE @tab TABLE(Id int)  
INSERT INTO @tab  
SELECT Id  
FROM SomeTable  
WHERE SomeDate = "10 DAYS AGO" 

SELECT *
FROM SomeOtherTable
INNER JOIN @tab t
ON SomeOtherTable.id = t.id  

--VERSUS--

SELECT *  
FROM SomeOtherTable  
INNER JOIN (SELECT Id FROM SomeTable WHERE SomeDate = "10 DAYS AGO") t  
ON SomeOtherTable.id = t.id

对于大型查询,如果您必须多次进行相同的联接,第一个更易于维护,但性能最高的是什么?

问候

【问题讨论】:

  • SELECT * FROM SomeOtherTable WHERE Id IN (SELECT Id FROM SomeTable WHERE SomeDate = "10 DAYS AGO") 怎么样,索引SomeDate 包括Id
  • 用 mysql 检查 explain,如果我没有错,一般来说你想要一个技巧来让内部(选择从)首先执行,从内到外执行。还有 google 用于 sql 查询优化或 sql join 优化
  • 我假设是 SQL Server,如果正确请告诉我。
  • @MartinSmith:非常正确,抱歉没有提及。大家:我没有创建索引的权限,也没有任何定义的ATM。(使用SCSM DWDataMart的人知道它)。我不时走进的专业人士不建议使用#temp 表。
  • @user972706 - 您需要针对您的具体情况进行测试。你还可以解释一下我想到的“多次加入相同的加入”的情况吗?如果是单个语句,请发布查询类型,并检查计划是否实际显示它被多次评估。

标签: sql sql-server performance database-performance


【解决方案1】:

SQL Server 不会维护表变量的详细统计信息,也不会自动重新编译以反映较小粒度的基数信息更改(没有 TF 2453),因此通常会假定它们输出单行。

这意味着有时您会得到一个次优的连接策略。第二个版本可以使用统计信息,也避免了将中间结果插入临时对象的开销。

但是,如果第二个查询的评估成本很高,因为 SomeDate 未编入索引,则您可以通过预先实现这一点来提高性能(与反复重新评估相比)。

您也可以考虑使用#temp 表,因为这样可以避免统计问题。 Some people suggest never using a table variable in JOINs

【讨论】:

    猜你喜欢
    • 2012-06-01
    • 2010-11-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-04-28
    • 2014-11-17
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多