我有一个存储过程,需要传递逗号分隔变量。使用逗号分隔值的VARCHAR参数创建IN子查询
例如,如果在一定条件存在,我会通过的国家代码的列表如下所示:
AU,RA,PK
的项数可以改变。
在存储过程中,我需要在IN
子句中使用这些物品,如如下:
WHERE CountryCode IN (@ExcludeCountries)
有没有办法做到这一点?如果需要的话,我可以按照国家代码进入类似N'AU', N'RA', N'PK'
的地方。
谢谢。
我有一个存储过程,需要传递逗号分隔变量。使用逗号分隔值的VARCHAR参数创建IN子查询
例如,如果在一定条件存在,我会通过的国家代码的列表如下所示:
AU,RA,PK
的项数可以改变。
在存储过程中,我需要在IN
子句中使用这些物品,如如下:
WHERE CountryCode IN (@ExcludeCountries)
有没有办法做到这一点?如果需要的话,我可以按照国家代码进入类似N'AU', N'RA', N'PK'
的地方。
谢谢。
WHERE CountryCode IN (SELECT *
FROM [dbo].[ufn_CSVToTable](@ExcludeCountries,',')
这是如何创建[dbo].[ufn_CSVToTable]
:
How to convert comma separated NVARCHAR to table records in SQL Server 2005?
有两种方法做到这一点:使用
建立这样
... + 'WHERE CountryCode IN' (' + @ExcludeCountries + ')' ...
动态SQL语句,然后用sp_executesql
来执行语句
但是要避免它 - 对于这样一个简单的任务,不需要使用动态SQL。 –
@Yosi完全不同意。我做了很多次,总是依赖于情况。您提供的解决方案在某些情况下可能会导致性能不佳,而使用动态SQL则可以解决此问题 - 这取决于您的情况。 – gotqn
在大多数情况下,当使用Dynamic Sql时 - 您在参数保护,代码可读性,查询编译和执行计划缓存以及可能反弹其他方面都失败了。你可以避免所有这些(甚至更好),但它更复杂。当子查询中有数千个值时,我的解决方案可能会导致性能不佳,用户是否描述过这种情况?我不这么认为...... –
在实践中我已经看到了使用下面的函数这个问题解决了。此函数分割字符串并返回包含指定值的表。然后使用它像这样...
... COUNTRYCODE IN(SELECT * FROM dbo.SplitString(@ExcludeCountries, ''))
注意,在这个例子中,逗号(” ,')是分隔符。我多年来一直使用这种方法,而且我没有遇到任何性能问题。
CREATE FUNCTION [dbo].[SplitString]
(
@SplitStr nvarchar(MAX),
@SplitChar nvarchar(5)
)
RETURNS @RtnValue table
(
Data nvarchar(MAX)
)
AS
BEGIN
Declare @Count int
Set @Count = 1
While (Charindex(@SplitChar,@SplitStr)>0)
Begin
Insert Into @RtnValue (Data)
Select
Data = ltrim(rtrim(Substring(@SplitStr,1,Charindex(@SplitChar,@SplitStr)-1)))
Set @SplitStr = Substring(@SplitStr,Charindex(@SplitChar,@SplitStr)+1,len(@SplitStr))
Set @Count = @Count + 1
End
Insert Into @RtnValue (Data)
Select Data = ltrim(rtrim(@SplitStr))
Return
END
我的答案已经提出了这个解决方案,为什么重复它? –
我没有注意到它,直到我写我的答案。我的答案仍然完整,无需弄清楚其他问题。 – fossilcoder
顺便说一句,正如你所看到的,我在这里是新的,我不认为重复的解决方案足以得到一个投票,它仍然解决了问题,并提供了一个完整的解决方案。 – fossilcoder
有一百万重复这个...简短的答案是传递一个表,如果你可以或使用其中一个解析函数。 – Hogan