从非规范化表中加载规范化表

时间:2016-12-19 22:38:37

标签: sql-server insert-into

我有一个如下表结构:

ID|Letter1|Letter2|Letter3|...n
-------------------------------
1    A       C       NULL  ...

2    A       D       D

3    P       F       M

使用select我必须将其加载到更加规范化的表中,如:

ID|Letter|
1    A
1    C
1    NULL
1    ...
2    A
2    D
2    D
3    P
3    F
3    M

我尝试过不同的方法:

INSERT INTO Normalized
 (ID, Letter)
SELECT ID, LETTER1
FROM Denormalized

对于信件的每次迭代,一遍又一遍地这样做。我的问题是,我有超过100个这个糟糕设计的字母字段,我试图围绕不同的想法,但没有任何结果。

我的问题是,是否有人知道将每个字母从非规范化表格插入规范化表格的动态方法,同时为每个字母创建不同的行?

1 个答案:

答案 0 :(得分:1)

statementFromTraversal

返回(带有XML的动态版本省略NULLS)

Declare @XML xml = (Select * from Denormalized for XML RAW)

INSERT INTO Normalized
Select ID     = r.value('@ID','int')
      --,Item   = attr.value('local-name(.)','varchar(100)')  -- Removed but will return Field Name
      ,Letter  = attr.value('.','varchar(max)') 
 From  @XML.nodes('/row') as A(r)
 Cross Apply A.r.nodes('./@*') AS B(attr)
 Where attr.value('local-name(.)','varchar(100)') not in ('ID')
  

编辑 - 要保留NULLS,另一种选择是使用交叉申请

ID  Letter
1   A
1   B
2   A
2   D
2   D
3   P
3   F
3   M

返回

INSERT INTO Normalized
Select A.ID
      ,B.Letter
 From  Denormalized A
 Cross Apply (Values 
              (A.Letter1)
             ,(A.Letter2)
             ,(A.Letter3)
             --...
             --,(A.LetterN)
             ) B (Letter)