合并同一外键的多个记录

时间:2014-03-14 01:03:12

标签: sql sql-server

源是存储过程中的一个透视表。我们知道前三列的列名,但其余部分是用户定义的,我们不会提前知道名称。这是一个例子:

CREATE TABLE Table1
    ([ID] int, [ReportID] int, [FieldID] int, [Col1] varchar(3), [Col2] int, [Col3] varchar(3));

INSERT INTO Table1
    ([ID], [ReportID], [FieldID], [Col1], [Col2], [Col3])
VALUES
    (1, 2, 1, 'abc', NULL, NULL),
    (2, 2, 2, NULL, 123, NULL),
    (3, 2, 3, NULL, NULL, 'A3A')
    (4, 3, 1, NULL, NULL, NULL),
    (5, 3, 2, NULL, 456, NULL),
    (6, 3, 3, 'def', NULL, NULL);

所需的输出是按ReportID对数据进行分组,当NULL值存在于同一ReportID的其他行中时,将NULL值替换为非NULL值。 ID列是数据透视表的产品,未使用。 FieldID列与其余列相关。

(1, 2, 1, 'abc', 123, A3A)
(4, 3, 1, 'def', 456, NULL)

我看了一下使用光标,但担心缩放。

我看过使用MERGE,但不知道列名,所以不能用列名来写它。

我们可以通过查询另一个表来访问用户定义列名的文本列表。

有什么想法吗?

1 个答案:

答案 0 :(得分:0)

您可以使用sys.columns系统视图创建动态sql,如下所示

    CREATE TABLE Table1
    ([ID] int, [ReportID] int, [FieldID] int, [Col1] varchar(3), [Col2] int, [Col3] varchar(3));

INSERT INTO Table1
    ([ID], [ReportID], [FieldID], [Col1], [Col2], [Col3])
VALUES
    (1, 2, 1, 'abc', NULL, NULL),
    (2, 2, 2, NULL, 123, NULL),
    (3, 2, 3, NULL, NULL, 'A3A'),
    (4, 3, 1, NULL, NULL, NULL),
    (5, 3, 2, NULL, 456, NULL),
    (6, 3, 3, 'def', NULL, NULL);

 declare @sql varchar(max)='select MIN(ID) ID, ReportID, MIN(FieldID) FieldID '

 select @sql+=',MIN('+c.name+') '+c.name from sys.columns c
 where object_id=object_id(N'table1')
        and c.name not in ('ID','ReportID','FieldID')


 select @sql+=' from table1 group by ReportID'

 exec (@sql)

 drop table Table1

但在这种情况下,您可能需要在sys.columns数据库的master上授予选择权限。

我认为,最好将数据分组到创建表的查询中。