Eri*_*ing 7

当发现一个简单的计划时,会尝试简单参数化。参数化尝试可能被认为是安全的不安全的

关键是找到一个琐碎的计划并被认为是安全的。如果琐碎计划的成本超过cost threshold for parallelism,优化器将继续进行优化的后期阶段,其中可能会考虑并行计划。无论最终结果是串行还是并行计划,如果找到(但最终未使用)的安全琐碎计划被参数化,它将被简单地参数化。

在问题示例中,设置cost threshold for parallelism高于平凡计划的成本将允许优化器在该阶段停止。


查看查询计划并不总是足以确定您的查询是否实际上是简单参数化的。

最安全的方法是检查一些 DMV 以验证:

/*Unsafe auto param*/
SELECT *
FROM sys.dm_os_performance_counters AS dopc
WHERE dopc.counter_name LIKE '%Unsafe Auto-Params/sec%';

/*Safe auto param*/
SELECT *
FROM sys.dm_os_performance_counters AS dopc
WHERE dopc.counter_name LIKE '%Safe Auto-Params/sec%';

/*Trivial Plans*/
SELECT * 
FROM sys.dm_exec_query_optimizer_info AS deqoi 
WHERE deqoi.counter = 'trivial plan';
Run Code Online (Sandbox Code Playgroud)

此外,您还可以使用未记录的跟踪标志 8607,但不能用作OPTION子句提示。使用OPTION子句可以防止一个琐碎的计划。

DBCC TRACEON(8607, 3604);
/*Wait*/    

/*Run*/     
SELECT u.CreationDate, u.Id
FROM dbo.Users AS u
WHERE u.Reputation = 2;

/*Clean up*/
DBCC TRACEOFF(8607, 3604);
Run Code Online (Sandbox Code Playgroud)

如果该计划对于简单参数化被认为是安全的,您将在此处看到一条确认消息。

********************

** Query marked as Cachable

** Query marked as Safe for Auto-Param
Run Code Online (Sandbox Code Playgroud)