2013-04-29 81 views
2

我想解释一个MSAccess中构建的查询,并将它变为SQL Server的可用SQL。ROW_NUMBER()和带有扭曲的GROUP BY

下面是访问SQL视图中的语句:

SELECT CUSTFILE.CUSTNUM, 
Last(GENPOL.eff_date) AS LastOfeff_date, 
First(GENPOL.appnum) AS FirstOfAPPNUM 

FROM GENPOL INNER JOIN CUSTFILE ON GENPOL.entnum = CUSTFILE.ENTNUM 

GROUP BY CUSTFILE.CUSTNUM 

HAVING... 

ORDER BY LastGENPOL.eff_date DESC; 

正如我们所知道的First()Last()功能在SQL Server中的无效和不工作,所以我试图用MIN()MAX()功能,因为该表没有增量ID字段或任何东西。一个大问题是,例如appnum可以有很奇怪的数据在它的领域,如:

MTP-021106 

OR

HMTP-271103 

因此,如果插入的最后appnumHMTP-271103和有更早的条目到genpol表像MTP-021106作为他们的申请

将比MTP-021106将返回,因为M大于H

此外,eff_date可能有相同的问题,因为最新的记录可能比最后一个输入具有更早的日期。

Last(GENPOL.eff_date) AS LastOfeff_date, 

最终的查询返回符合HAVING条件的每个CUSTFILE.CUSTNUM一行。

我相信可能是一个答案是使用ROW_NUMBER()函数来获得我需要的结果,但一直无法使它与GROUP BY语句一起工作。

表GENPOL:

 
(PK)appnum, varchar(13) 
eff_date, datetime 
ntnum, varchar(15) 

表CUSTFILE:

 
(PK)CUSTNUM, varchar(8) 
ENTNUM, varchar(15) 

示例数据

 
CUSTNUM | LastOfeff_date | FirstOfAppnum 
MI99103 | 2013-01-01 | MTP-991103 
MI99104 | 2013-01-01 | MTP-991104 
MI99105 | 2013-01-01 | MTP-991105 
+2

如果您发布了表结构,样本数据和期望的结果,这将非常有帮助。 – Taryn 2013-04-29 17:33:28

+0

“ENTITY”应该被别名为'CUSTFILE'吗? – valverij 2013-04-29 18:40:23

+0

是,已编辑。 – Trelmoz 2013-04-29 18:51:44

回答

2

编辑:固定一个参考列中的一

基于你所列出的东西,这样的事情应该工作:

SELECT 
    cfile.CUSTNUM, 
    aGENPOL.eff_date [LastOfeff_date], 
    bGENPOL.appnum [FirstOfAPPNUM] 
FROM CUSTFILE cfile 
CROSS APPLY (
    SELECT TOP 1 * 
    FROM (
     SELECT ROW_NUMBER() OVER(PARTITION BY entnum ORDER BY entnum) row, eff_date 
     FROM GENPOL 
     WHERE entnum = cfile.entnum   
    ) x 
    ORDER BY row DESC 
) aGENPOL 
CROSS APPLY (
    SELECT TOP 1 * 
    FROM (
     SELECT ROW_NUMBER() OVER(PARTITION BY entnum ORDER BY entnum) row, appnum 
     FROM GENPOL 
     WHERE entnum = cfile.entnum 
    ) y 
    ORDER BY row 
) bGENPOL 

基本上,在查询申请将由每个entnum分区表抢每种情况的顶级记录,然后按行号排序(首先升序,最后降序)。

由于加入的查询相当复杂,我还选择使用CROSS APPLY,因为它本质上是在进行连接之前过滤记录。

+0

完美!结果正是我所期待的。非常感谢您的帮助。 – Trelmoz 2013-04-29 20:44:38