郭某人的网站

关于 / 留言

.NET Framework 参数化 SQL 查询 in、like 问题

C# 使用 SqlParameter 类参数化执行 in、like SQL 语句时错误异常的解决方案


在 .NET Framework 的项目程序中,我们可能会进行参数化查询数据库的操作,在参数与类型一一对应的情况下通常是没问题的,但是如果涉及到 like、in 这种从句的参数化,我们第一时间想到的可能会是下面这样:

SqlCommand cmd = new SqlCommand();
cmd.CommandText = "select count(1) from table_1 where ID in (@ID)";
cmd.Parameters.Add(new SqlParameter("@ID", "1,2"));

假设有表 table_1,其中有 ID inttitle nvarchar(max) 两列,这时我们用上面的参数化查询代码就会出现数据类型的错误,因为 "1,2" 属于字符串,不能直接被转换为 int 整数,因为此表中 ID 列需要是 int 类型的值,如果传入的是可被转换为 int 整数的值,比如去掉其中的逗号那又是行的,可见从语法上这没有问题,可能是该参数化内部做出了对应参数与其类型的强匹配、校验、转换等操作。

此时我的快速解决方案是把 SQL 命令当作用户自定义函数来执行,也就是用 EXEC 命令组合字符串,再进行参数化传递,如下:

SqlCommand cmd = new SqlCommand();
cmd.CommandText = "exec('select count(1) from table_1 where ID in (' + @ID + ')')";
cmd.Parameters.Add(new SqlParameter("@ID", "1,2"));

我没有具体研究过 System.Data.SqlClient.SqlParameter 应用的原理,不过我发现可以把这种方案视为与下面的 T-SQL 语句功能相同,至少结果相同:

declare @ID nvarchar(max)
set @ID = '1,2'
exec('select count(1) from table_1 where ID in (' + @ID + ')')
 
select count(1) from dt_friend_links where ID in (1,2)
 
declare @title nvarchar(max)
set @title = 'a'
exec('select count(1) from table_1 where title like ''%' + @title +'%''')
 
select count(1) from dt_friend_links where title like '%a%'

我没有测试过这种方案会不会对参数化本身的一些特点造成影响,比如影响 SQL 注入安全性,或者影响效率等等,不过如果不这样的话,那不是又只能预拼接 SQL 字符串来进行数据库操作了?


最后更新时间:2025/08/07 14:50

我好像也并没有那么差钱~

注意!你的赞赏转账请考虑再三后支付,此收款不作任何形式的退款。