在我的SELECT语句中,我使用的可选参数的方式是这样的:可选参数,“索引查找”计划
DECLARE @p1 INT = 1
DECLARE @p2 INT = 1
SELECT name FROM some_table WHERE (id = @p1 OR @p1 IS NULL) AND (name = @p2 OR @p2 IS NULL)
在这种情况下,优化器生成“索引扫描”(不求)操作的实体当参数提供非空值时,这不是最有效的。
如果我将RECOMPILE提示添加到查询中,优化器将使用“seek”构建更有效的计划。它适用于我的MSSQL 2008 R2 SP1服务器,这也意味着优化器可以构建一个只考虑我的查询的一个逻辑分支的计划。
我该如何使它能够在任何地方使用该计划,而不需要重新编译?在这种情况下,USE PLAN暗示图标不起作用。
下面是测试代码:
-- see plans
CREATE TABLE test_table(
id INT IDENTITY(1,1) NOT NULL,
name varchar(10),
CONSTRAINT [pk_test_table] PRIMARY KEY CLUSTERED (id ASC))
GO
INSERT INTO test_table(name) VALUES ('a'),('b'),('c')
GO
DECLARE @p INT = 1
SELECT name FROM test_table WHERE id = @p OR @p IS NULL
SELECT name FROM test_table WHERE id = @p OR @p IS NULL OPTION(RECOMPILE)
GO
DROP TABLE test_table
GO
请注意,并非所有的SQL Server版本将改变我的计划显示的方式。
谢谢你的回复。是的,我知道其他解决方法与寻求 - 使用IFs,重构SQL等。但很遗憾,我不能提供查询与优化器只为这个查询建立的计划... – LINQ2Vodka