0

我可以使用游标来做到这一点,但如果可能的话,我会尽量避免它。这是我要进行的一些示例代码:

declare @string varchar(max) = 'person1:item1~item2~item3~etc^person2:item1~item2~item3~etc'

declare @table1 table (id int, value varchar(500))
declare @table2 table (id varchar(50), value varchar(500))
declare @table3 table (id varchar(50), value varchar(50))

insert @table1 (id, value) select * from fn_ParseDelimitedStrings(@string, '^')

insert @table2 (id, value) 
    select 
        id = (select f.value from fn_ParseDelimitedStrings(t.value, ':') f where f.RowId=1),
        value = (select f.value from fn_ParseDelimitedStrings(t.value, ':') f where f.RowId=2)
    from @table1 t

select * from @table2

上面的代码以以下形式为我提供了数据:

id        value
-------------------------------
person1   item1~item2~item3~etc
person2   item1~item2~item3~etc

但我需要这种形式的数据:

id        value
-------------------------------
person1   item1
person1   item2
person1   item3
person1   etc
person2   item1
person2   item2
person2   item3
person3   etc

输入字符串可以有任意数量的“persons”,每个人可以有任意数量的“items”。

fn_ParseDelimitedStrings是我们拥有的一个自定义函数,它为每个分隔项返回一个索引值对表。IE:

RowID   Value
-------------
1       item1
2       item2
3       item3
4       etc

我无法将最终拆分中的每个“项目”与它们应该关联的“人”关联起来。

有什么可以做的还是我必须使用光标?

4

1 回答 1

2

外部应用将当前行与外部应用内部派生表中找到的所有行连接起来:

insert @table2 (id, value) 
select 
    id = (select f.value from fn_ParseDelimitedStrings(t.value, ':') f where f.RowId=1),
    value = v1.value
from @table1 t
outer apply
(
  select v.value
    from fn_ParseDelimitedStrings(
         (select f.value 
            from fn_ParseDelimitedStrings(t.value, ':') f 
           where f.RowId=2)
         , '~') v 
) v1

*将 value1 编辑为 v1 以匹配最外层的选择

于 2012-08-08T17:33:09.870 回答