MSSQL拆分字符串函数性能糟糕

时间:2018-09-25 09:47:12

标签: c# asp.net sql-server stored-procedures

我有两个单独的查询/方法和函数,这样我就可以在存储过程中传递两个字符串,基本上是这样的:

1234,12346,12690812,1259081 => UPCList parameter

1234,12346,12690812,1259081 => EANList parameter

现在第一种方法如下:

create procedure [dbo].[zsp_selectallupceans_list]
(
@UPCList nvarchar(4000),
@EANList nvarchar(4000),
@Type tinyint
)
as

select DISTINCT dd.UPC,dd.EAN,dd.EBAYID as ItemID
from ThirdPartyData  as dd 
where dd.UPC in (SELECT * FROM dbo.SplitString(@UPCList)) OR
dd.EAN in (SELECT * FROM dbo.SplitString(@EANList)) and dd.Type=@Type

结合在MSSQL中创建的splitstring函数:

create FUNCTION [dbo].[splitstring] ( @stringToSplit VARCHAR(MAX) )
RETURNS
 @returnList TABLE ([Name] [nvarchar] (500))
AS
BEGIN

 DECLARE @name NVARCHAR(255)
 DECLARE @pos INT

 WHILE CHARINDEX(',', @stringToSplit) > 0
 BEGIN
  SELECT @pos  = CHARINDEX(',', @stringToSplit)  
  SELECT @name = SUBSTRING(@stringToSplit, 1, @pos-1)

  INSERT INTO @returnList 
  SELECT @name

  SELECT @stringToSplit = SUBSTRING(@stringToSplit, @pos+1, LEN(@stringToSplit)-@pos)
 END

 INSERT INTO @returnList
 SELECT @stringToSplit

 RETURN
END

现在是第二种方法:

create procedure [dbo].[zsp_selectallupceans_listProduction]
(
@UPCList nvarchar(4000),
@EANList nvarchar(4000),
@Type tinyint
)
as


SELECT  dd.UPC,dd.EAN,dd.EBAYID as ItemID
from ThirdPartyData  as dd 
WHERE EXISTS (SELECT 1 FROM dbo.SplitStringProduction(@UPCList,',') S1 WHERE dd.UPC=S1.val) 
   OR EXISTS (SELECT 1 FROM dbo.SplitStringProduction(@EANList,',') S2 WHERE dd.EAN=S2.val) and dd.Type=@Type

现在是第二个方法splitstringProduction:

create FUNCTION [dbo].[SplitStringProduction]
(
  @string nvarchar(max),
  @delimiter nvarchar(5)
) RETURNS @t TABLE
(
  val nvarchar(500)
)
AS
BEGIN
  declare @xml xml
  set @xml = N'<root><r>' + replace(@string,@delimiter,'</r><r>') + '</r></root>'

  insert into @t(val)
  select 
    r.value('.','varchar(500)') as item
  from @xml.nodes('//root/r') as records(r)

  RETURN
END

现在出现了奇怪的部分...两种方法的基准测试结果如下:

  var findEans = ctx.zsp_selectallupceans_list(formedList.UPCList, formedList.EANList, 1).ToList();
//Execution time 4.8 seconds

 var findEans = ctx.zsp_selectallupceans_listProduction(formedList.UPCList, formedList.EANList, 1).ToList();
//Execution time: 15 seconds

据我所知,第二种方法的执行速度应比第一种方法快得多……但这不是这种情况……第二种方法的性能不仅较差,而且执行时间也超过3倍比第一个...我不明白为什么...

伙计们这是怎么回事?将执行时间减少到<1秒的最佳方法是什么?

有人可以帮我吗?

0 个答案:

没有答案