SQL SERVER: T-sql Spilt string into multiple columns

Have a SQL table with one column having string value. I need to split the string into multiple columns showing Drive name and the Space

Drive c:\ has 66 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space
Drive c:\ has 68 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space
Drive c:\ has 68 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space
Drive c:\ has 63 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space
Drive c:\ has 66 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space
expected result, please find attached.String.PNG
Harman BajwaAsked:
Who is Participating?
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

PortletPaulfreelancerCommented:
I would do it a little differently, instead of multiple drive & percentages per row, I would do just one per row. e.g.
CREATE TABLE YourTable
    ([id] int, [longstring] varchar(500))
;
  
INSERT INTO YourTable
    ([id], [longstring])
VALUES
    (1, 'Drive c:\ has 66 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space'),
    (2, 'Drive c:\ has 68 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space'),
    (3, 'Drive c:\ has 68 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space'),
    (4, 'Drive c:\ has 63 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space'),
    (5, 'Drive c:\ has 66 percent free disk space. Drive d:\ has 99 percent free disk space. Drive e:\ has 99 percent free disk space. Drive k:\ has 99 percent free disk space')
;

Open in new window

YOu need a "split string" function, here is one (there are many)
CREATE FUNCTION dbo.Split_String /* dbo.SplitStrings_Moden https://sqlperformance.com/2012/07/t-sql-queries/split-strings */
(
   @List NVARCHAR(MAX),
   @Delimiter NVARCHAR(255)
)
RETURNS TABLE
WITH SCHEMABINDING AS
RETURN
  WITH E1(N)        AS ( SELECT 1 UNION ALL SELECT 1 UNION ALL SELECT 1 UNION ALL SELECT 1 
                         UNION ALL SELECT 1 UNION ALL SELECT 1 UNION ALL SELECT 1 
                         UNION ALL SELECT 1 UNION ALL SELECT 1 UNION ALL SELECT 1),
       E2(N)        AS (SELECT 1 FROM E1 a, E1 b),
       E4(N)        AS (SELECT 1 FROM E2 a, E2 b),
       E42(N)       AS (SELECT 1 FROM E4 a, E2 b),
       cteTally(N)  AS (SELECT 0 UNION ALL SELECT TOP (DATALENGTH(ISNULL(@List,1))) 
                         ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) FROM E42),
       cteStart(N1) AS (SELECT t.N+1 FROM cteTally t
                         WHERE (SUBSTRING(@List,t.N,1) = @Delimiter OR t.N = 0))
SELECT 
    Item = SUBSTRING(@List, s.N1, ISNULL(NULLIF(CHARINDEX(@Delimiter,@List,s.N1),0)-s.N1,8000))
FROM cteStart s
;

Open in new window

This can then be used in a query like so:
select
      id
    , x.item, y.pos
    , replace(replace(left(item,pos),'Drive ',''),':','') as drive
    , replace(replace(substring(item,pos,500),':\ has ',''),' percent free disk space','') as percent_free
from yourtable
cross apply dbo.split_string(longstring,'.') x
cross apply (select charindex(':\',item) as pos) y  
 

Open in new window

which produces:
| id |                                      item | pos | drive | percent_free |
|----|-------------------------------------------|-----|-------|--------------|
|  1 |  Drive c:\ has 66 percent free disk space |   8 |     c |           66 |
|  1 |  Drive d:\ has 99 percent free disk space |   9 |     d |           99 |
|  1 |  Drive e:\ has 99 percent free disk space |   9 |     e |           99 |
|  1 |  Drive k:\ has 99 percent free disk space |   9 |     k |           99 |
|  2 |  Drive c:\ has 68 percent free disk space |   8 |     c |           68 |
|  2 |  Drive d:\ has 99 percent free disk space |   9 |     d |           99 |
|  2 |  Drive e:\ has 99 percent free disk space |   9 |     e |           99 |
|  2 |  Drive k:\ has 99 percent free disk space |   9 |     k |           99 |
|  3 |  Drive c:\ has 68 percent free disk space |   8 |     c |           68 |
|  3 |  Drive d:\ has 99 percent free disk space |   9 |     d |           99 |
|  3 |  Drive e:\ has 99 percent free disk space |   9 |     e |           99 |
|  3 |  Drive k:\ has 99 percent free disk space |   9 |     k |           99 |
|  4 |  Drive c:\ has 63 percent free disk space |   8 |     c |           63 |
|  4 |  Drive d:\ has 99 percent free disk space |   9 |     d |           99 |
|  4 |  Drive e:\ has 99 percent free disk space |   9 |     e |           99 |
|  4 |  Drive k:\ has 99 percent free disk space |   9 |     k |           99 |
|  5 |  Drive c:\ has 66 percent free disk space |   8 |     c |           66 |
|  5 |  Drive d:\ has 99 percent free disk space |   9 |     d |           99 |
|  5 |  Drive e:\ has 99 percent free disk space |   9 |     e |           99 |
|  5 |  Drive k:\ has 99 percent free disk space |   9 |     k |           99 |

Open in new window

I have assumed there is some colun like ID in your existing table.

nb some columns dislayed only to make it easier to follow the logic

NOTE: if using SQL Server 2017 here is an inbuilt STRING_SPLIT() function and you can use it instead
select
      id
    , x.value, y.pos
    , replace(replace(left(value,pos),'Drive ',''),':','') as drive
    , replace(replace(substring(value,pos,500),':\ has ',''),' percent free disk space','') as percent_free
from yourtable
cross apply string_split(longstring,'.') x
cross apply (select charindex(':\',value) as pos) y  
;

Open in new window

see http://sqlfiddle.com/#!18/be0b8/2
0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
SQL

From novice to tech pro — start learning today.

Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.