1

I am using below function to split the string into multiple strings everything is working fine but i need to store the results into multiple variables

instead of that the results are storing into a table

this is my query

DECLARE @strngLen int
DECLARE @split TABLE(siteId VARCHAR(100))

DECLARE @city varchar(100), @state varchar(100), @zip varchar(100)

SET @siteIds = 'OMAHA  NE  68117'

SET @strngLen = CHARINDEX('  ', @siteIds)

WHILE CHARINDEX('  ', @siteIds) > 0
BEGIN
    SET @strngLen = CHARINDEX('  ', @siteIds);

    INSERT INTO @split
    SELECT SUBSTRING(@siteIds,1,@strngLen - 1);

    SET @siteIds = SUBSTRING(@siteIds, @strngLen+1, LEN(@siteIds));
END

INSERT INTO @split
SELECT @siteIds

SELECT * FROM @split

---Here i need to store the @siteIds into multiple local variables 
---like in (@city varchar(100), @state varchar(100), @zip varchar(100)) 
3
  • What are you asking? How to split a string (dozens of faster duplicates) or how to write the SELECT @thisvariable=... statement ? How about the standard answer - don't try parsing on the server? Splitting will fail if a name contains spaces Commented Jun 19, 2017 at 8:36
  • I think his question is how to put the result in a different variable on each iteration Commented Jun 19, 2017 at 8:37
  • You can directly assign the characters before the first space as City to city variable and so on if the string is going to be in the same order. Commented Jun 19, 2017 at 8:38

3 Answers 3

4

if they are always in the same order and same separator then there is not need for a loop, this will do all the job:

DECLARE @siteIds varchar(100)
DECLARE @city varchar(100), @state varchar(100), @zip varchar(100)

SET @siteIds = 'OMAHA  NE  68117'

select @city=(parsename(replace(@siteIds,'  ','.'),3)),
       @state=(parsename(replace(@siteIds,'  ','.'),2)),
       @zip=(parsename(replace(@siteIds,'  ','.'),1))
Sign up to request clarification or add additional context in comments.

Comments

0

If there is going to be only 3 strings (cit,state and zip) then the below select will fetch you the result.

declare @str1 varchar(10)
declare @str2 varchar(10)

select @city= substring(@siteIds,1,charindex('  ',@siteIds)-1)
,@str1 = substring(@siteIds,charindex('  ',@siteIds)+1,len(@siteIds))
,@state = substring(@str1,1,charindex('  ',@str1)-1)
,@str2 = substring(@str1,charindex('  ',@str1)+1,len(@str1))
,@zip = substring(@str2,1,len(@str2))

4 Comments

getting error at this line 'Invalid length parameter passed to the LEFT or SUBSTRING function.' at this line substring(@siteIds,1,charindex(' ',@siteIds)-1)
two spaces between each strings
It will start fetching from the first character till the city name + single space. No clue about the error in that substring function.
Have you tried executing only the first substring which will fetch the city?
0

First, the standard answer - don't do this on the server. It's far easier to parse strings on the client.

Second, this isn't as trivial as it appears - this is parsing, not splitting a string. In this case, each token has a different meaning. All string splitting techniques, and the STRING_SPLIT command return a table of unordered tokens.

Third, the splitting technique is one of the slowest, and can't be modified parse instead of split. The fastest techniques are SQLCLR and XML parsing. Both can be modified to return a table with multiple columns.

For example, the following XML parsing function:

CREATE FUNCTION dbo.SplitStrings_XML
(
   @List       NVARCHAR(MAX),
   @Delimiter  NVARCHAR(255)
)
RETURNS TABLE
WITH SCHEMABINDING
AS
   RETURN 
   (  
      SELECT Item = y.i.value('(./text())[1]', 'nvarchar(4000)')
      FROM 
      ( 
        SELECT x = CONVERT(XML, '<i>' 
          + REPLACE(@List, @Delimiter, '</i><i>') 
          + '</i>').query('.')
      ) AS a CROSS APPLY x.nodes('i') AS y(i)
   );
GO

works by surrounding each token with i tags, producing <i>OMAHA</i><i>NE</i><i>68117</i>. Then it selects the contents of each I element with tags with CROSS APPLY x.nodes('i')

You can modify it to nest the elements and return the 1st, 2nd and 3rd element, as follows:

CREATE FUNCTION dbo.SplitTriplets_XML
(
   @List       NVARCHAR(MAX),
   @Delimiter  NVARCHAR(255)
)
RETURNS TABLE
WITH SCHEMABINDING
AS
   RETURN 
   (  
      SELECT    
        Item1 = o.i.value('@value', 'nvarchar(4000)'),
        Item2 = p.i.value('@value', 'nvarchar(4000)'),
        Item3 = q.i.value('@value', 'nvarchar(4000)')
      FROM 
      ( 
        SELECT x = CONVERT(XML, '<i value="' 
          + REPLACE(@List, @Delimiter, '"><i value="') 
          + '"></i></i></i>').query('.')
      ) AS a 
              OUTER APPLY x.nodes('/i') AS o(i)
              OUTER APPLY x.nodes('/i/i') AS p(i)
              OUTER APPLY x.nodes('/i/i/i') AS q(i)
  )

In this case, the generated XML is <i value="OMAHA"><i value="NE"><i value="68117" /></i></i> and the OUTER APPLY x.nodes('/i') AS p(i) statements select the root and nested tags as separate tables.

This example :

declare @table table (id int,value nvarchar(200))
insert into @table
values
(1,'OMAHA  NE  68117'),
(2,'sdfA  Nw  68227')

select id,value,item1 as City,item2 as State,item3 as Zip
from @table x cross apply dbo.SplitTriplets_XML(value,'  ')

Returns :

id          value             City   State  Zip   
----------- ----------------- ------ ------ ------
1           OMAHA  NE  68117  OMAHA  NE     68117
2           sdfA  Nw  68227   sdfA   Nw     68227

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.