sql server相关子查询无法下推外层过滤条件,导致外层每行触发内层全表扫描,时间复杂度为o(n×m);而等价join可一次性完成,效率更高。

嵌套查询每行都触发一次内层扫描
SQL Server 对相关子查询(比如 WHERE x > (SELECT MAX(y) FROM t2 WHERE t2.id = t1.ref_id))无法下推外层过滤条件,导致外层表每处理一行,内层表就重新全表扫描一遍。哪怕外层只有 100 行,内层表被扫了 100 次——这本质上是 O(N×M) 时间复杂度,而等价的 JOIN 可借助哈希或合并连接一次性完成。
优化器难以为非等值嵌套生成高效执行计划
嵌套查询中若含 BETWEEN、>、 等非等值条件,SQL Server 无法使用哈希连接或合并连接,只能退化为嵌套循环(Nested Loops),且内表几乎无法利用索引查找——除非你提前建好覆盖索引(如 <code>CREATE INDEX ix_t2_ref_x ON t2(ref_id, x) INCLUDE (y))。但即便如此,仍受限于外层行数和统计信息准确性。
JOIN 能启用更优的物理连接算法
等值连接(ON a.id = b.id)让优化器有选择余地:
• 小表驱动大表 → 嵌套循环 + 索引查找
• 两表都已排序 → 合并连接(Merge Join)
• 大表无序 → 哈希匹配(Hash Match)
而嵌套查询直接锁死执行路径,连 hint(如 OPTION (HASH JOIN))都无效。
三层以上嵌套可能根本解析失败
这不是慢的问题,是跑不起来:
• SQL Server 解析器对 CTE 递归深度默认限制为 MAXRECURSION 100,超限直接报错
• 多层标量子查询叠加 WITH + UNION ALL + ORDER BY,容易耗尽解析栈,报 ERROR 1038 (HY001) 或静默中断
• 执行计划里甚至看不到 SELECT 节点,因为语法树都没构建成功
APPLY、窗口函数或预计算分桶,而不是硬扛嵌套。











