将多行组合成一行,数据分为两列

时间:2015-12-12 02:09:04

标签: sql sql-server-2008

我有一个以下方式的SQL表:

Table_Name  Field_Name       New_Value  Create_Date     
TableTest   Loading Hours       25      12/12/2015  2:56:26 p.m.    
TableTest   Loading Hours       15      12/12/2015  2:30:23 p.m.    
TableTest   Loading Hours       11      12/12/2015  2:09:42 p.m.    
TableTest   Loading_Percentage  35.8    12/12/2015  2:56:26 p.m.    
TableTest   Loading_Percentage  15.5    12/12/2015  2:30:23 p.m.    

我想要做的是能够改变上述内容,我如何才能有效地做到这一点?我可能在上表中的加载时间内有更多的值,这需要逻辑显示,如下面的转换数据中所示。

TableTest   Field_Name         OldValue NewValue   DateTime 
TableTest   Loading Hours       15       25        12/12/2015   2:56:26 p.m.
TableTest   Loading Hours       11       15        12/12/2015   2:30:23 p.m.
TableTest   Loading Hours       NULL     11        12/12/2015   2:09:42 p.m.
TableTest   Loading_Percentage  15.5     35.8      12/12/2015   2:56:26 p.m.
TableTest   Loading_Percentage  NULL     15.5      12/12/2015   2:30:23 p.m.

提前感谢您的帮助。

干杯

2 个答案:

答案 0 :(得分:0)

您的场景正是lag窗口函数的设计目标。遗憾的是,lag在SQL Server 2008中不可用。在升级之前,您可以执行以下操作:

with cte as (
  select *,
         row_number() over (partition by table_name, field_name order by create_date) as rn
    from tbl
)
select curr.table_name,
       curr.field_name,
       prev.new_value as old_value,
       curr.new_value,
       curr.create_date
  from cte curr
  left join cte prev
    on prev.table_name = curr.table_name
   and prev.field_name = curr.field_name
    on prev.rn = curr.rn + 1
 order by curr.table_name, curr.field_name, curr.rn desc

如果您升级到SQL Server 2012+,可以使用lag更简单地编写查询,并获得良好的性能提升:

select table_name,
       field_name,
       lag(new_value) over (partition by table_name, field_name order by create_date) as old_value,
       new_value,
       create_date
  from tbl
 order by table_name, field_name, create_date desc

答案 1 :(得分:0)

在Trigger中处理此方案。为表添加“插入”和“更新”触发器,并使用触发器实现所需的功能。 当将数据插入/更新到表中时,触发器应根据Field_Name获取最后插入/更新的值,并插入具有新旧值的新记录。