разделение поля с разделителями на отдельные столбцы в одной записи - PullRequest
2 голосов
/ 27 сентября 2011

Мне нужно разделить поле с разделителями трубы ('Y | N | Y | Y').

Я нашел рекурсивную функцию, перечисленную здесь T-SQL: в отличие от конкатенации строк - как разбить строку на несколько записей

, но она создает значения в новых записях.

row   field
 1      Y
 2      N
 3      Y
 4      N

Мне нужно преобразовать 'Y | N | Y | Y'

field
'Y|N|Y|Y' 

в

field1  |  field2  | field3  | field4
    y         N         Y        N

Может ли кто-нибудь указать мне правильное направление?Было бы проще, если бы я сказал, что число значений фиксировано (вероятно, это будет 8 значений, разделенных в одном поле).

Обновление: Возможное значение поля может быть этим (примечаниепустое значение): 'Y | 10 | N | 1 || Y'

Ответы [ 2 ]

1 голос
/ 27 сентября 2011

** РЕДАКТИРОВАТЬ: ** Шахта все еще работает для образца строки

Вот альтернативный ответ, поскольку вы знаете, что ширина имеет фиксированную длину:

DECLARE @myString AS nvarchar(20) = 'Y|10|N|1||Y'

;WITH cte
AS
(
SELECT
    KeyCol = @@IDENTITY,
    CONVERT(XML,'<i>' + REPLACE(@myString, '|', '</i><i>') + '</i>') AS delimited_str
)
SELECT 
    [1] AS Field1,
    [2] AS Field2,
    [3] AS Field3,
    [4] AS Field4,
    [5] AS Field5,
    [6] AS Field6,
    [7] AS Field7,
    [8] AS Field8
FROM(
    SELECT 
        KeyCol,
        ROW_NUMBER() OVER (partition by KeyCol order by KeyCol)as col_nbr,
        x.i.value('.', 'VARCHAR(50)') AS delimited_VAL
    FROM cte
    CROSS APPLY delimited_str.nodes('//i') AS x(i)
    ) as PivotedDataTable
PIVOT
(MAX(delimited_VAL) FOR col_nbr IN
([1], [2], [3], [4], [5], [6], [7], [8])
) AS PivotTable;

РЕДАКТИРОВАТЬ: я знал, что видел это где-то раньше, когда я столкнулся с аналогичной проблемой: http://social.msdn.microsoft.com/Forums/en-US/transactsql/thread/381e4164-f1e0-4b54-828f-2795d2cdcb3e/

1 голос
/ 27 сентября 2011

Если ширина полей также всегда фиксирована, т. Е. 1 символ (Y / N), то это просто, как использование функции substring для получения всех значений отдельных полей:

;with Data as (
    select 'Y|N|Y|Y' as choices union
    select 'Y|Y|Y|Y' as choices union
    select 'Y|N|N|Y' as choices union
    select 'Y|N|N|N' as choices union
    select 'N|N|Y|N' as choices union
    select 'Y|Y|N|Y' as choices
)
select
    substring(choices, 1, 1) as field1,
    substring(choices, 3, 1) as field2,
    substring(choices, 5, 1) as field3,
    substring(choices, 7, 1) as field4
from
    Data

Вывод:

field1  field2  field3  field4
N       N       Y       N
Y       N       N       N
Y       N       N       Y
Y       N       Y       Y
Y       Y       N       Y
Y       Y       Y       Y

Если вы не можете гарантировать одинаковую ширину полей, вы можете использовать charindex и вспомогательную таблицу индексов полей для генерации вывода, который выищем.Это становится очень многословным, так как число полей увеличивается, но вам нужно будет написать его только один раз, если число полей будет фиксированным:

;with Data as (
    select 1 as id, 'Y|N|Y|Y' as choices union
    select 2,'Y|Y|Y|Y' as choices union
    select 3,'Y|No|N|Y' as choices union
    select 4,'Yes|N|N|N' as choices union
    select 5,'N|N|Yes|No' as choices union
    select 6,'Y|Y|N|Yes' as choices
), Fields as (
    select
        id,
        charindex('|', choices) as field1end,
        charindex('|', choices, charindex('|', choices) + 1) as field2end,
        charindex('|', choices, charindex('|', choices, charindex('|', choices) + 1) + 1) as field3end,
        len(choices) + 1 as field4end
    from
        Data
)
select
    substring(choices, 1, field1end - 1) as field1,
    substring(choices, field1end + 1, field2end - field1end - 1) as field2,
    substring(choices, field2end + 1, field3end - field2end - 1) as field3,
    substring(choices, field3end + 1, field4end - field3end - 1) as field4
from
    Data D
inner join
    Fields F on D.id = F.id

Вывод:

field1  field2  field3  field4
Y       N       Y       Y
Y       Y       Y       Y
Y       No      N       Y
Yes     N       N       N
N       N       Yes     No
Y       Y       N       Yes
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...