症状
当您用许多行填充表变量,然后将其与其他表联接时,查询优化器可能会选择效率低下的查询计划,这可能导致查询性能下降。
解决方法
应用此修补程序后,可以打开跟踪标志 2453 以允许表变量在更改足够数量的行时触发重新编译。 这可能允许查询优化器选择更高效的计划。
此问题已首先在以下 SQL Server 累积更新或/和 Service Pack 中修复。
SQL Server 2014 累积更新 3 /en-us/help/2984923
关于 SQL Server 的累积更新
SQL Server 的每个新累积更新都包含上一个累积更新中包含的所有修补程序和所有安全修补程序。 查看 SQL Server 的最新累积更新:
SQL Server 2012 Service Pack 2
关于 SQL Server 的 Service Pack
Service Pack 具有累积性。 每个新 Service Pack 除了包含所有新修复程序外,还包含以前 Service Pack 中的所有修复程序。 建议应用最新的 Service Pack 和该 Service Pack 的最新累积更新。 在安装最新的 Service Pack 之前,不需要安装以前的 Service Pack。 使用以下文章中的表 1 查找有关最新 Service Pack 和最新累积更新的详细信息:
如何确定 SQL Server 及其组件的版本、版本类别和更新级别
详细信息
在批次或过程中使用表变量时,将针对表变量的初始空状态编译和优化查询。 如果此表变量在运行时填充了许多行,则预编译的查询计划可能不再是最佳的。 例如,查询可能会使用嵌套循环加入表变量,因为它通常对于少量行更有效。 如果表变量有数百万行,则此查询计划可能效率低下。 在这种情况下,哈希加入可能是更好的选择。 若要获取新的查询计划,需要对其进行重新编译。 但是,与其他用户表或临时表不同,表变量中的行计数更改不会触发查询重新编译。 通常情况下,可以使用 OPTION (RECOMPILE) 来解决此问题,这有自己的开销成本。
跟踪标志 2453 允许在没有 OPTION (RECOMPILE) 的情况下进行查询重新编译。 此跟踪标志在两个主要方面与 OPTION (RECOMPILE) 不同。
(1) 它使用与其他表相同的行计数阈值。 与 OPTION (RECOMPILE) 不同,不需要为每次执行都编译该查询。 仅当行计数更改超过预定义的阈值时,才会触发重新编译。
(2) 选项 (重新编译) 强制查询速览参数并为其优化查询。 此跟踪标志不强制参数速览。
请注意,此跟踪标志在运行时必须为 ON。 不能将此跟踪标志与 QUERYTRACEON 一起使用。 必须谨慎使用此跟踪标志,因为它可能会增加查询重新编译的次数,这可能比更好的查询优化所节省的成本更高。
状态
Microsoft 已确认在 "适用于" 部分中所列的 Microsoft 产品中存在问题。