Where IN 逗号分隔的字符串
Where IN a Comma delimited string
我想从临时 table #temptable 的完整列表中检索某些用户。
查询如下所示:
DECLARE @List varchar(max)
SELECT @List = coalesce(@List + ',','') + '''' + StaffCode + ''''
FROM tblStaffs
SELECT UserName
FROM #temptable
WHERE #temptable.StaffCode IN (@List)
我可以看出@List 的格式是正确的:
'AAA','ABB','BBB','CCC','DDD','MMM'
如果我将其更改为
WHERE #temptable.StaffCode IN ('AAA','ABB','BBB','CCC','DDD','MMM')
当然可以,那为什么不在 (@List) 中呢?
创建一些拆分字符串函数并将逗号分隔值转换为行,然后您可以使用转换后的行 IN
子句
DECLARE @List VARCHAR(max)
SELECT @List = COALESCE(@List + ',', '') +StaffCode
FROM tblStaffs
SELECT UserName
FROM #temptable
WHERE #temptable.StaffCode IN (SELECT split_values
FROM dbo.Splitstring_function(@list))
检查 here 各种拆分字符串函数
如果你不想创建函数那么你也可以直接使用代码而不是创建一个新函数(M.Ali的答案)。
另一种方法是使用 dynamic query
.
Declare @List varchar(max), @sql nvarchar(max)
Select @List = coalesce(@List + ',','') + '''' + StaffCode + ''''
From tblStaffs
set @sql = '
Select UserName
From #temptable
Where #temptable.StaffCode IN ('+ @List + ')'
--print @sql
exec (@sql)
调试动态查询总是print
动态sql在执行之前。
我建议您根本不要使用逗号分隔的字符串。考虑 semi-join 代替:
select [Temp].[UserName]
from
#temptable [Temp]
where
exists (select 1 from [tblStaffs] where [tblStaffs].[StaffCode] = [Temp].[StaffCode]);
因为变量有一个字符串,IN 运算符读取为 'AAA'',''ABB'',''BBB'
并将其视为单个值。
在您的查询中,您应该真正在 IN
运算符中使用查询本身,例如....
Select UserName
From #temptable
Where #temptable.StaffCode IN (SELECT StaffCode From tblStaffs)
无论如何,如果需要使用变量,然后从该变量读取 IN
运算符中的值,您可以这样做....
DECLARE @List VARCHAR(1000);
Select @List = coalesce(@List + ',','') + StaffCode
From tblStaffs
SELECT *
From #temptable
Where #temptable.StaffCode IN (
SELECT t.c.value('.', 'VARCHAR(1000)')
FROM (
SELECT x = CAST('<t>' +
REPLACE(@List , ',', '</t><t>') + '</t>' AS XML)
) a
CROSS APPLY x.nodes('/t') t(c))
我想从临时 table #temptable 的完整列表中检索某些用户。 查询如下所示:
DECLARE @List varchar(max)
SELECT @List = coalesce(@List + ',','') + '''' + StaffCode + ''''
FROM tblStaffs
SELECT UserName
FROM #temptable
WHERE #temptable.StaffCode IN (@List)
我可以看出@List 的格式是正确的:
'AAA','ABB','BBB','CCC','DDD','MMM'
如果我将其更改为
WHERE #temptable.StaffCode IN ('AAA','ABB','BBB','CCC','DDD','MMM')
当然可以,那为什么不在 (@List) 中呢?
创建一些拆分字符串函数并将逗号分隔值转换为行,然后您可以使用转换后的行 IN
子句
DECLARE @List VARCHAR(max)
SELECT @List = COALESCE(@List + ',', '') +StaffCode
FROM tblStaffs
SELECT UserName
FROM #temptable
WHERE #temptable.StaffCode IN (SELECT split_values
FROM dbo.Splitstring_function(@list))
检查 here 各种拆分字符串函数
如果你不想创建函数那么你也可以直接使用代码而不是创建一个新函数(M.Ali的答案)。
另一种方法是使用 dynamic query
.
Declare @List varchar(max), @sql nvarchar(max)
Select @List = coalesce(@List + ',','') + '''' + StaffCode + ''''
From tblStaffs
set @sql = '
Select UserName
From #temptable
Where #temptable.StaffCode IN ('+ @List + ')'
--print @sql
exec (@sql)
调试动态查询总是print
动态sql在执行之前。
我建议您根本不要使用逗号分隔的字符串。考虑 semi-join 代替:
select [Temp].[UserName]
from
#temptable [Temp]
where
exists (select 1 from [tblStaffs] where [tblStaffs].[StaffCode] = [Temp].[StaffCode]);
因为变量有一个字符串,IN 运算符读取为 'AAA'',''ABB'',''BBB'
并将其视为单个值。
在您的查询中,您应该真正在 IN
运算符中使用查询本身,例如....
Select UserName
From #temptable
Where #temptable.StaffCode IN (SELECT StaffCode From tblStaffs)
无论如何,如果需要使用变量,然后从该变量读取 IN
运算符中的值,您可以这样做....
DECLARE @List VARCHAR(1000);
Select @List = coalesce(@List + ',','') + StaffCode
From tblStaffs
SELECT *
From #temptable
Where #temptable.StaffCode IN (
SELECT t.c.value('.', 'VARCHAR(1000)')
FROM (
SELECT x = CAST('<t>' +
REPLACE(@List , ',', '</t><t>') + '</t>' AS XML)
) a
CROSS APPLY x.nodes('/t') t(c))