我的SQL Server数据库中有一些错误的数据。
看起来像这样:
abc.qwerty@yahoo.com|fubar@cc.uk|helloworld@gmail.com
或
abc.qwerty@yahoo.com;fubar@cc.uk
如果分隔符可以是“|
”,“;
”,“,
”中的任何一个,如何将它们拆分为单独的电子邮件。
分割后,结果将添加到同一个表中的3列:
Email1: abc.qwerty@yahoo.com, Email2: fubar@cc.uk, Email3: helloworld@gmail.com
答案 0 :(得分:1)
DECLARE @STR NVARCHAR(MAX)='abc.es@yahoo.com|shudo@cc.uk|maria@gmail.com, abc.es@yahoo.com;shudo@cc.uk'
-- Converts values to rows
SELECT Split.a.value('.', 'VARCHAR(100)') 'Ids'
FROM
(
-- Use 3 REPLACE for '|', ';', ','
SELECT CAST ('<M>' + REPLACE(REPLACE(REPLACE(@STR, '|', '</M><M>'),',','</M><M>'),';','</M><M>') + '</M>' AS XML) AS Data
) AS A
CROSS APPLY Data.nodes ('/M') AS Split(a)
<强>更新强>
如果您想将逗号分隔值作为最终字符串,则可以执行以下操作
DECLARE @STR NVARCHAR(MAX)='abc.qwerty@yahoo.com|fubar@cc.uk|helloworld@gmail.com,abc.qwerty@yahoo.com;fubar@cc.uk '
DECLARE @Final VARCHAR(MAX)='';
-- Converts values to rows
;WITH CTE AS
(
SELECT DISTINCT
Split.a.value('.', 'VARCHAR(100)') 'Ids'
FROM
(
-- Use 3 REPLACE for '|', ';', ','
SELECT CAST ('<M>' + REPLACE(REPLACE(REPLACE(@STR, '|', '</M><M>'),',','</M><M>'),';','</M><M>') + '</M>' AS XML) AS Data
) AS A
CROSS APPLY Data.nodes ('/M') AS Split(a)
)
-- Convert to Comma Seperated Values
SELECT @Final +=
Isnull('Email' + CAST(ROW_NUMBER() OVER(ORDER BY IDS)AS VARCHAR(10)) + ': ' + Ids, '') + ', '
FROM CTE
SELECT LEFT(@Final,len(@Final)-1)
PRINT @Final
更新2:拆分分隔符将值分隔为行并动态转换为列
我在查询中写了逻辑
DECLARE @STR NVARCHAR(MAX)='abc.es@yahoo.com|shudo@cc.uk|maria@gmail.com,abc.es@yahoo.com;shudo@cc.uk'
;WITH CTE AS
(
-- Converts values to rows
SELECT DISTINCT Split.a.value('.', 'VARCHAR(100)') 'Ids'
FROM
(
-- Use 3 REPLACE for '|', ';', ','
SELECT CAST ('<M>' + REPLACE(REPLACE(REPLACE(@STR, '|', '</M><M>'),',','</M><M>'),';','</M><M>') + '</M>' AS XML) AS Data
) AS A
CROSS APPLY Data.nodes ('/M') AS Split(a)
)
-- Create a column to order Emails like Email1,Email2.... and insert to a temp table
-- It can be done without temp table, but its for sake of readability
SELECT 'Email' + CAST(ROW_NUMBER() OVER(ORDER BY Ids)AS VARCHAR(10)) EMails,Ids
INTO #TEMP
FROM CTE
-- Get columns to pivot
DECLARE @cols NVARCHAR (MAX)
SELECT @cols = COALESCE (@cols + ',[' + EMails + ']','[' + EMails + ']')
FROM (SELECT DISTINCT EMails FROM #TEMP) PV
ORDER BY EMails
-- Pivot the result(convert to columns from rows)
DECLARE @query NVARCHAR(MAX)
SET @query = 'SELECT * FROM
(
SELECT EMails,Ids
FROM #TEMP
) x
PIVOT
(
MIN(Ids)
FOR EMails IN (' + @cols + ')
) p;'
EXEC SP_EXECUTESQL @query
现在,如果您要将电子邮件插入到已创建的表中,可以使用以下代码
DECLARE @query NVARCHAR(MAX)
SET @query = 'INSERT INTO YOURTABLE(' + @cols + ')
SELECT * FROM
(
SELECT EMails,Ids
FROM #TEMP
) x
PIVOT
(
MIN(Ids)
FOR EMails IN (' + @cols + ')
) p;'
EXEC SP_EXECUTESQL @query
答案 1 :(得分:0)
第一步我会清理你的数据。 SQL Server具有您可以使用的Replace
功能。
REPLACE ( string_expression , string_pattern , string_replacement )
您可以在SQL Server Management Studio中运行的示例:
select Replace(Replace('ab|de,ghi;de', ',', '|'), ';', '|')
首先会替换逗号,然后是分号。导致ab|de|ghi|de
或者,您可以通过在生成的拆分上运行游标(使用您用于拆分的任何机制)来多次拆分数据。