首页 > 解决方案 > 选择表中的第二个最小值

问题描述

我有一个如下表,最初我想返回不同状态的最早更新日期。但是,由于项目被取消并重新创建,我想忽略第一个计划日期,只返回第二个计划日期。

+------------+------------+------------+---------- -+
| 项目编号 | 更新DT | 审核 ID | 子状态 |
+------------+------------+------------+---------- -+
| 11111 | 2017-12-20 | 10123 | 规划 |
| 11111 | 2017-05-25 | 10135 | 规划 |
| 11111 | 2017-10-11 | 10254 | 取消 |
+------------+------------+------------+---------- -+

我的查询如下所示,但它只能返回最早的计划日期,而不是第二个最早的日期。我添加了一个 CASE 表达式,但结果仍然相同。任何人都可以请点亮一些灯吗?谢谢你。

SELECT DISTINCT sub.Request_ID
    ,sub.UpdateDT
    ,a.reqStatus
FROM [RptChange].[dbo].[tRequestsAudit] a
JOIN (
    SELECT [reqID] [Request_ID]
        ,CASE 
            WHEN [reqStatus] IN ('Cancelled')
                THEN MAX([reqUpdateDt])
            ELSE MIN([reqUpdateDt])
            END AS [UpdateDT]
        ,MIN([AuditID]) AS EarliestAuditID
        ,[reqStatus] SubStatus
    FROM [RptChange].[dbo].[tRequestsAudit]
    WHERE [reqID] = 11111
    GROUP BY [reqStatus]
        ,[reqID]
    ) sub ON sub.[EarliestAuditID] = a.AuditID
+------------+------------+------------+---------- -+
| 项目编号 | 更新DT | 审核 ID | 子状态 |
+------------+------------+------------+---------- -+
| 11111 | 2017-05-25 | 10135 | 规划 |
| 11111 | 2017-10-11 | 10254 | 取消 |
+------------+------------+------------+---------- -+

我想要的结果:

+------------+------------+------------+---------- -+
| 项目编号 | 更新DT | 审核 ID | 子状态 |
+------------+------------+------------+---------- -+
| 11111 | 2017-12-20 | 10123 | 规划 |
| 11111 | 2017-10-11 | 10254 | 取消 |
+------------+------------+------------+---------- -+

标签: sqlsql-server

解决方案


这是使用 ROW_NUMBER 解决此问题的一种方法。

declare @tRequestsAudit table
(
    ProjectID int
    , UpdateDT date
    , AuditID int
    , SubStatus varchar(10)
)

insert @tRequestsAudit values
(11111, '2017-12-20', 10123, 'Planning')
, (11111, '2017-05-25', 10135, 'Planning')
, (11111, '2017-10-11', 10254, 'Cancelled')
;

select ProjectID
    , UpdateDT
    , AuditID
    , SubStatus
from
(
    select *
        , RowNum = ROW_NUMBER()over(partition by ProjectID, SubStatus order by UpdateDT desc)
    from @tRequestsAudit
) x
where x.SubStatus <> 'Planning'
OR
(
    x.SubStatus = 'Planning'
    AND
    x.RowNum = 2
)

推荐阅读