根据最近的日期窗口选择结果

Posted

技术标签:

【中文标题】根据最近的日期窗口选择结果【英文标题】:Select results based on nearest date window 【发布时间】:2020-09-18 00:03:34 【问题描述】:

我有一个如下的 SQL Server 表。我想按名称和参加考试的地点分组,根据上述分组按日期升序排列。

现在提供了一个可配置的窗口,例如:4 天。在下表中,如果第一次考试日期是 2019 年 2 月 1 日(2 月 1 日) - 其分数已被计入,并且在接下来的 4 天窗口内重新获得的任何其他考试分数将不予考虑。如果记录也在已经排除的项目示例行 id - 4 的 4 天窗口内,则也应排除。

非常感谢此逻辑的任何 SQL 语句。

CREATE TABLE test(  
    [recordid] int IDENTITY(1,1) PRIMARY KEY,
    [name] [nvarchar](25) NULL,
    [testcentre] [nvarchar](25) NULL,
    [testdate] [smalldatetime] NOT NULL,
    [testscore] [int],
    [Preferred_Output] [int],
    [Result] [nvarchar](75) NULL
)

GO
INSERT INTO test
           (
    [name],
    [testcentre],
    [testdate],
    [testscore],
    [Preferred_Output],
    [Result]  )
    VALUES
('George','bangalore',' 02/01/2019',1,1,'Selected as first item -grouped by name and location'),
('George','bangalore',' 02/02/2019',0,0,'ignore as within 4 days'),
('George','bangalore',' 02/04/2019',1,0,'ignore as within 4 days'),
('George','bangalore',' 02/06/2019',3,0,'ignore as within 4 days from already ignored item -04-02-2019'),
('George','bangalore',' 02/15/2019',2,2,'Selected as second item -grouped by name and location'),
('George','bangalore',' 02/18/2019',5,0,'ignore as within 4 days of previous'),
('George','Pune',' 02/15/2019',4,3,'Selected as third item'),
('George','Pune',' 02/18/2019',6,0,'ignore as within 4 days of previous'),
('George','Pune',' 02/19/2019',7,0,'ignore as within 4 days of previous'),
('George','Pune',' 02/20/2019',8,0,'ignore as within 4 days of previous')

GO
select * from test
GO



+----------+--------+------------+------------+-----------+------------------+
| recordid |  name  | testcentre |  testdate  | testscore | Preferred_Output |
+----------+--------+------------+------------+-----------+------------------+
|        1 | George | bangalore  | 02/01/2019 |         1 |                1 |
|        2 | George | bangalore  | 02/02/2019 |         0 |                0 |
|        3 | George | bangalore  | 02/04/2019 |         1 |                0 |
|        4 | George | bangalore  | 02/06/2019 |         3 |                0 |
|        5 | George | bangalore  | 02/15/2019 |         2 |                2 |
|        6 | George | bangalore  | 02/18/2019 |         5 |                0 |
|        7 | George | Pune       | 02/15/2019 |         4 |                3 |
|        8 | George | Pune       | 02/18/2019 |         6 |                0 |
|        9 | George | Pune       | 02/19/2019 |         7 |                0 |
|       10 | George | Pune       | 02/20/2019 |         8 |                0 |
+----------+--------+------------+------------+-----------+------------------+

【问题讨论】:

你试过什么?向我们展示你的尝试? 【参考方案1】:

我认为这不需要递归查询。您想比较连续记录中的日期,所以这是一种间隙和岛屿问题,要确定每个岛屿的开始。

窗口函数可以做到这一点:

select t.*,
    case when lag_testdate is null or testdate > dateadd(day, 4, lag_testdate)
        then testscore
        else 0
    end new_core
from (
    select t.*, lag(testdate) over(partition by name, testcentre order by testdate) lag_testdate
    from test t
) t

Demo on DB Fiddle

【讨论】:

您好 GMB,想添加一个重新测试条件以及使用 RANK 函数的延迟,这是正确的方法吗? dbfiddle.uk/…

以上是关于根据最近的日期窗口选择结果的主要内容,如果未能解决你的问题,请参考以下文章

根据上次日期选择记录

根据最近的日期从多个相似的行中选择一行

根据日期仅选择每条记录的最新版本 | MS Access [重复]

SQL:根据最近的日期选择一个字段中的值是唯一的记录

Oracle 根据返回不一致结果的年份选择日期

AngularJS - 出现在模态后面的日期选择器