查询可以工作,但当把它放在存储过程中时就不行了;不起作用

本文关键字:过程中 存储过程 存储 不起作用 不行了 工作 查询 | 更新日期: 2023-09-27 18:00:43

我测试下面的查询并正常工作

select * from tbl where userName in ('A','B','C')

但是当我创建一个存储过程并将参数传递给它时,不起作用(参数是正确的)

SqlCommand sc = new SqlCommand("exec example @userName",...
sc.Parameters.AddWithValue("@userName", "'A','B','C'");
...
// Stored Procedure
create procedure example 
    @users varchar(100)
as
    select * from tbl where userName in ('@users')

查询可以工作,但当把它放在存储过程中时就不行了;不起作用

不要将参数放在引号中。

然而,仅仅拥有:

select * from tbl where userName in (@users)

也不起作用,因为您正试图对恰好表示元素列表的字符串使用in函数。

您需要将字符串转换为数组,然后在select语句中使用它:

MSDN有一个这样做的示例函数:

CREATE FUNCTION dbo.Split 
   (  @Delimiter varchar(5), 
      @List      varchar(8000)
   ) 
   RETURNS @TableOfValues table 
      (  RowID   smallint IDENTITY(1,1), 
         [Value] varchar(50) 
      ) 
AS 
   BEGIN
      DECLARE @LenString int 
      WHILE len( @List ) > 0 
         BEGIN 
            SELECT @LenString = 
               (CASE charindex( @Delimiter, @List ) 
                   WHEN 0 THEN len( @List ) 
                   ELSE ( charindex( @Delimiter, @List ) -1 )
                END
               ) 
            INSERT INTO @TableOfValues 
               SELECT substring( @List, 1, @LenString )
            SELECT @List = 
               (CASE ( len( @List ) - @LenString ) 
                   WHEN 0 THEN '' 
                   ELSE right( @List, len( @List ) - @LenString - 1 ) 
                END
               ) 
         END
      RETURN 
    END 

然后这样使用:

select * from tbl where userName in (SELECT * FROM dbo.Split( ',', @users ))
众所周知,

"in"查询很难参数化。首先,不要把参数放在引号里,否则它就不是参数:它是一个字符文字。但是:您也不能仅仅使用单个参数,因为这将搜索一个只包含引号和逗号的值,而不是您想要的。

这里有各种方法;例如,在服务器上使用"split"函数,并对该结果进行内部联接。然而,一些工具也有帮助。例如,"dapper"允许进行语法调整:

var names = new List<string> { "A", "B", "C" };
var users = connection.Query<User>(
    "select * from users where name in @names",
    new { names }).ToList();

库使用多个参数将其扩展为正确的"in"查询。