2016-01-25 45 views
0

Ms SQL Server。表中的历史'分片'

我有一张表,用于监视学生的学校申请状态。 学生可以申请多个学校,每个学校都可以接受/拒绝/等待学生的名单。

tblApplicantSchools会是这个样子:

ApplicantID | SchoolID  |  StatusID 

独特的申请者可以出现在这里申请多所学校 - 但每个学校的申请之一的地位。

我也有一个历史性的表tblApplicantSchools_shadow,它会影响tblApplicantSchools上所做的任何更改。它与上面的内容相同,只是它还节省了更改的时间,以及它是否是原始表上的插入/更新/删除。 因此,在他shadow表中,可能有多个学生,有多个状态的多个学校(当他们在整个过程中移动时)。

我想要做的是将shadow表格分到一定的日期,并将每个申请的单个最近的statusID带到每个申请人的每个学校。这有意义吗? 例如:

ApplicantID | SchoolID  |  StatusID  | ChangeDate 
----------------------------------------------------------------------- 
    11     2     3     22/1/2015 
    11     2     4     30/1/2015 
    11     3     4     25/1/2015 
    11     3     6     29/1/2015 

所以,我希望看到的是仅列#2和上面第4,被视为他们的申请#11到每个学校的最近期更新。

有人能给我一个关于如何做到这一点的指针吗?我的设置稍微复杂一些,但我认为这个例子简化了它,这样问题就很清楚了。

感谢

回答

1

如果你希望一个ANSI-92标准的解决方案,或者如果你怕的窗口功能,那么这个查询可能是有用的:

SELECT s1.ApplicantID, s1.SchoolID, s1.StatusID, s1.ChangeDate 
FROM shadow s1 
INNER JOIN 
(
    SELECT ApplicantID, SchoolID, MAX(ChangeDate) AS maxDate 
    FROM shadow 
    GROUP BY ApplicantID, SchoolID 
) s2 
ON s1.ApplicantID = s2.ApplicantID AND s1.SchoolID = s2.SchoolID 
    AND s1.ChangeDate = s2.maxDate 
2

你可以使用窗口函数ROW_NUMBER

SELECT * 
FROM (SELECT *, rn = ROW_NUMBER() OVER(PARTITION BY ApplicantID,SchoolID 
             ORDER BY ChangeDate DESC) 
     FROM tblApplicantSchools_shadow) AS sub 
WHERE rn = 1; 

LiveDemo

输出:

╔═════════════╦══════════╦══════════╦═════════════════════╗ 
║ ApplicantID ║ SchoolID ║ StatusID ║  ChangeDate  ║ 
╠═════════════╬══════════╬══════════╬═════════════════════╣ 
║   11 ║  2 ║  4 ║ 2015-01-30 00:00:00 ║ 
║   11 ║  3 ║  6 ║ 2015-01-29 00:00:00 ║ 
╚═════════════╩══════════╩══════════╩═════════════════════╝ 

请记住,如果ChangeDate只是DATE(没有时间标准,有可能会打平,您应该使用RANK()来代替。与DATETIME平局的概率很低。

+1

这肯定看起来像是我想学习,谢谢。看起来很强大。现在太多太多了,我们正在寻找另一种更加不错的解决方案。 – kneidels