2013-06-03 2 views
1

Я просто хочу знать, как я могу получить значения, используя выбор из столбца с строковым разделителем.Получить значения из столбца с строковым делителем

Ex: значение столбца:

';#10;~Banana;#101;~Apple' 

Как я могу получить эти значения и сохранить в таблице, как это?

code description 
    10  Banana 
    101 Apple 

, похоже, не может получить его с помощью подстроки, charindex combo. Должен ли я использовать функцию вместо этого? В принципе, этот столбец имеет потенциал для хранения более 100 значений (код/​​desc).

+1

ли данные, хранящиеся как это? Или это для импорта из текстового файла? – gbn

+0

Является ли это SQL Server или Sybase? – Pondlife

+0

Да, данные хранятся в столбце как заданное значение выборки в таблице SQL Server – jackCaller

ответ

2

Попробуйте это с помощью метода XML Nodes (SQL-FIDDEL)

DECLARE @S VARCHAR(500)= ';#10;~Banana;#101;~Apple' 

--REMOVE LEADING ROW DELIMETER `;#` 
SELECT @S = SUBSTRING(@S,3, LEN(@S)) 


DECLARE @X XML 
SELECT @X = '<myxml><nodes><n1>' + 
REPLACE(REPLACE (@S,';#','</n2></nodes><nodes><n1>'),';~','</n1><n2>') + 
'</n2></nodes></myxml>' 


SELECT C.value('n1[1]','VARCHAR(50)') AS code, 
     C.value('n2[1]','VARCHAR(50)') AS description 
FROM @X.nodes('/myxml/nodes') Cols (C) 


| CODE | DESCRIPTION | 
---------------------- 
| 10 |  Banana | 
| 101 |  Apple | 
+0

хороший ... это именно то, что мне нужно. Большое спасибо Kaf! :) – jackCaller

+0

привет, Kaf, не уверен, что нормально отвечать на другой вопрос ... но есть сценарий, когда мне нужно только вернуть описание ТОЛЬКО в одной строке, разделенной запятой ','. Это возможно? TIA :) – jackCaller

+0

Я думаю, вы можете сделать это с помощью UDF. Передайте строковый столбец функции и верните отфильтрованный список описаний csv. Для этого вы можете использовать встроенные строковые функции, такие как 'Charindex',' Substring' и 'left/right'. – Kaf

0

Вы можете попробовать выше (вместо '' использования ';'):

CREATE FUNCTION dbo.fnSplit(
    @sInputList VARCHAR(8000) -- List of delimited items 
    , @sDelimiter VARCHAR(8000) = ',' -- delimiter that separates items 
) RETURNS @List TABLE (item VARCHAR(8000)) 

BEGIN 
DECLARE @sItem VARCHAR(8000) 
WHILE CHARINDEX(@sDelimiter,@sInputList,0) <> 0 
BEGIN 
SELECT 
    @sItem=RTRIM(LTRIM(SUBSTRING(@sInputList,1,CHARINDEX(@sDelimiter,@sInputList,0)-1))), 
    @sInputList=RTRIM(LTRIM(SUBSTRING(@sInputList,CHARINDEX(@sDelimiter,@sInputList,0)+LEN(@sDelimiter),LEN(@sInputList)))) 

IF LEN(@sItem) > 0 
    INSERT INTO @List SELECT @sItem 
END 

IF LEN(@sInputList) > 0 
INSERT INTO @List SELECT @sInputList -- Put the last item in 
RETURN 
END 
GO 



select * from dbo.fnSplit('1,22,333,444,,5555,666', ',') 

Results 

Item 

1 
22 
333 
444 
5555 
666 
+0

Ссылка только ответы не являются хорошими ответами. Если связь умирает, ответ становится бесполезным. Просьба подытожить основные части страницы в фактическом ответе. – ChrisF

+0

Вы абсолютно правы. Я починю это. –

0

Или просто подстроку по ';'

select 
    substr(column, INSTR(column, ';', 1, 1)+1, 
    (INSTR(column, ';', 1, 2) - INSTR(column, 1, 1)) 
    ) col_a, 
    substr(column, INSTR(column, ';', 1, 2)+1, 
    (INSTR(column, ';', 1, 3) - INSTR(column, ';', 1, 2)) 
    ) col_b 
from dual 

Рабочий пример:

select 
    substr(';#10;~Banana;#101;~Apple', INSTR(';#10;~Banana;#101;~Apple', ';', 1, 1)+1, 
    (INSTR(';#10;~Banana;#101;~Apple', ';', 1, 2) - INSTR(';#10;~Banana;#101;~Apple', ';', 1, 1)) 
    ) col_a, 
    substr(';#10;~Banana;#101;~Apple', INSTR(';#10;~Banana;#101;~Apple', ';', 1, 2)+1, 
    (INSTR(';#10;~Banana;#101;~Apple', ';', 1, 3) - INSTR(';#10;~Banana;#101;~Apple', ';', 1, 2)) 
    ) col_b 
from dual 
Смежные вопросы