创建SQL查询以查找最近的字段更改

时间:2014-03-27 21:26:04

标签: sql common-table-expression

我在尝试创建SQL查询时遇到问题,以便选择最近几小时的更改以及与之前记录的时间的差异。

该表如下所示,数据库按版本保存所有历史版本:

Item    ID        Title           RevisedDate       ChangedDate       Rev      WorkHours
Task    187061    Development     10/9/12 11:14     10/5/12 15:54     1        4
Task    187061    Development     10/9/12 14:29     10/9/12 11:14     2        8
Task    187061    Development     10/10/12 15:07    10/9/12 14:29     3        16
Task    187061    Development     10/11/12 9:59     10/10/12 15:07    4        16
Task    187061    Development     10/12/12 10:51    10/11/12 9:59     5        16
Task    187061    Development     12/6/12 15:25     10/12/12 10:51    6        16
Task    187061    Development     12/11/12 10:27    12/6/12 15:25     7        16
Task    187061    Development     1/1/99 0:00       12/11/12 10:27    8        16

因此,最近工作时间的任务在10月10日15:07从8小时更新到16小时。我在创建查询时遇到问题告诉我。

在一天结束时,我需要一个结果: -

Item    ID      Title           RevisedDate     ChangedDate     Rev   WorkHours   ChangeHours
Task    187061  Development     10/10/12 15:07  10/9/12 14:29   3     16          8

(p.s我以一个任务为例,实际表有数百个任务和几个历史版本)

1 个答案:

答案 0 :(得分:0)

据我了解您的问题,您希望该项目包含每个ID的最新修订日期

你是这样的:

SELECT * 
FROM
(
  SELECT *, 
         ROW_NUMBER() OVER (PARTITION BY ID ORDER BY RevisedDate DESC) as ord
  FROM TABLE
) T
WHERE ord = 1

如果你想要第一个更改的那个更难:

-- First find the ones that changed
With FlagChange AS
(
  SELECT T1.ID, T1.REV, T1.RevisedDate 
         CASE WHEN T2 IS NULL THEN FALSE
              WHEN T1.WorkHour != T2.WorkHour THEN TRUE 
              ELSE FALSE END AS Changed
  FROM TABLE T1
  LEFT JOIN TABLE T2 ON T1.ID = T2.ID AND T2.REV = T1.REV-1
), NumberChange -- now use row number
(
  SELECT ID, REV,
  ROW_NUMBER() OVER (PARTITION BY ID ORDER BY RevisedDate DESC) as ord
  FROM FlagChange
  WHERE Changed = True
), SelectRecent -- take the newest ones
(
  SELECT ID, REV
  FROM NumberChange
  WHERE ord = 1
)  -- add in all the data and the ones with one revision
SELECT *
FROM TABLE T1
JOIN SelectRecient SR ON T1.ID = SR.ID AND T1.REV = SR.REV
UNION ALL
SELECT *
FROM TABLE 
WHERE ID NOT IN (SELECT ID FROM SelectRecent)