微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

在SQL中处理’可选’where子句过滤器的正确方法?

假设您有一个存储过程,它需要一个可选参数.您希望在SQL查询中使用此可选参数.通常这就是我看到它完成的方式:
SELECT * FROM dbo.MyTableName t1
WHERE t1.ThisField = 'test'
AND (@MyOptionalParam IS NULL OR t1.MyField = @MyOptionalParam)

这似乎运行良好,但如果您使用STATISTICS IO ON运行查询,则会导致大量逻辑读取.我也尝试了以下变体:

SELECT * FROM dbo.MyTableName t1
WHERE t1.ThisField = 'test'
AND t1.MyField = CASE WHEN @MyOptionalParam IS NULL THEN t1.MyField ELSE @MyOptionalParam END

并且它产生相同数量的高读数.如果我们将sql转换为字符串,然后在其上调用sp_Executesql,则读取几乎为零:

DECLARE @sql nvarchar(max)

SELECT @sql = 'SELECT * FROM dbo.MyTableName t1
WHERE t1.ThisField = ''test'''

IF @MyOptionalParam IS NOT NULL
BEGIN
     SELECT @sql = @sql + ' AND t1.MyField = @MyOptionalParam '
END

EXECUTE sp_Executesql @sql,N'@MyOptionalParam',@MyOptionalParam

我疯了吗?为什么选择哪些条款如此难以正确?

更新:我基本上问是否有办法将标准语法保留在存储过程中并获得低逻辑读取,如sp_Executesql方法.构建一个字符串对我来说似乎完全疯了……更不用说它使得维护,调试,可视化变得更加困难.

解决方法

If we convert the sql to a string,then call sp_Executesql on it,the reads are almost nil…

>因为您的查询不再评估OR,因为您可以看到杀死sargability
>使用sp_executesql时缓存查询计划; sql Server不必进行硬解析……

优秀资源:The Curse & Blessing of Dynamic SQL

只要您使用参数化查询,就应该从SQL Injection attacks开始安全.

原文地址:https://www.jb51.cc/mssql/84093.html

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐