基于日期逻辑的案例子查询

时间:2016-12-20 20:53:40

标签: sql sql-server sql-server-2008

我正在将此数据作为转换过程的一部分插入另一个表中。不幸的是,我无法在源位置或目标位置修改表架构。

我有以下源数据:(显然只是数据的一个小快照)

Id  StudentID   Score   Createdate
1   1           86      2015-09-15 12:59:46.000
2   1           89      2015-09-15 12:59:46.000
3   1           76      2015-09-15 12:59:46.000
4   1           91      2015-10-14 13:45:33.000
5   1           87      2015-10-14 13:45:33.000
6   1           78      2015-10-14 13:45:33.000
7   1           88      2015-10-14 13:45:33.000
8   2           78      2014-10-23 09:21:17.000
9   2           82      2014-10-23 09:21:17.000
10  2           83      2014-10-23 09:21:17.000

我的最终结果目标数据应如下所示:

Id  StudentID   TestType    Score   Createdate
1   1           Pretest     86      2015-09-15 12:59:46.000
2   1           Pretest     89      2015-09-15 12:59:46.000
3   1           Pretest     76      2015-09-15 12:59:46.000
4   1           Posttest    91      2015-10-14 13:45:33.000
5   1           Posttest    87      2015-10-14 13:45:33.000
6   1           Posttest    78      2015-10-14 13:45:33.000
7   1           Posttest    88      2015-10-14 13:45:33.000
8   2           Pretest     78      2014-10-23 09:21:17.000
9   2           Pretest     82      2014-10-23 09:21:17.000
10  2           Pretest     83      2014-10-23 09:21:17.000

基本上,出现的逻辑是,对于给定的学生,每个数据记录的最早创建被认为是预测试。对于同一个学生,同一创建者的任何和所有后续记录也是预测试。对于具有后期创建者的同一学生的任何记录,它们都被认为是后测。

我可能会在insert语句中使用case语句,因为我还有其他数据元素,这些数据元素也会在转换中出现。

为简单起见,我的脚本如下所示:

INSERT INTO targettable
(id,
studentid,
testtype,
score,
createdate)
SELECT DISTINCT
id          = sourcetable.id,
studentid   = sourcetable.studentid,
testtype    = CASE
                WHEN ????
              END
score       = sourcetable.score,
createdate  = sourcetable.createdate
FROM sourcetable

我的问题是,我不确定如何处理逻辑来确定基于createdate的pretest / posttest测试类型。

有什么想法吗?

提前致谢

1 个答案:

答案 0 :(得分:3)

您可以使用dense_rank()rank()

执行此操作
select t.*,
       (case when dense_rank() over (partition by studentId
                                     order by cast(createdate as date)
                                    ) = 1
             then 'Pretest'
             else 'Posttest'
        end) as TestType
from sourcetable t;