You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何计算同列中员工最近两条考勤记录的日期差(天数)

解决思路:用窗口函数简化日期差计算

你已经成功用ROW_NUMBER()拿到了每个员工最近两条考勤记录,卡在日期差计算上很正常——自关联确实容易踩坑,比如关联条件没精准匹配到对应的相邻记录,或者日期转换时格式不对导致计算错误。试试用窗口函数来解决,逻辑更清晰,也不容易出错。

问题分析

你之前尝试自关联计算日期差,但结果不正确,大概率是两个原因:

  • 自关联时没有限定只取同员工的最近两条记录,导致匹配到了更早的考勤数据;
  • 日期转换时没指定正确的格式掩码,数据库解析日期出错,进而差值计算错误。

解决方案

方案1:每条记录都显示两条的日期差(符合你的第一个期望输出)

用MAX()和MIN()窗口函数,在同员工分区内直接计算最近两条记录的日期差,然后过滤出前两条记录即可:

SELECT 
    T1.EMPNO AS Id,
    T1.ATT_DATE AS Date,
    -- 计算当前员工最近两条考勤的日期差
    TRUNC(
        MAX(TO_DATE(T1.ATT_DATE, 'MM/DD/YYYY')) OVER(PARTITION BY T1.EMPNO) 
        - MIN(TO_DATE(T1.ATT_DATE, 'MM/DD/YYYY')) OVER(PARTITION BY T1.EMPNO)
    ) AS Days
FROM (
    SELECT 
        T2.EMPNO, 
        T2.ATT_DATE,
        ROW_NUMBER() OVER(PARTITION BY T2.EMPNO ORDER BY TO_DATE(T2.ATT_DATE, 'MM/DD/YYYY') DESC) AS rn
    FROM TableName T2
) T1
WHERE T1.rn <= 2
ORDER BY T1.EMPNO, TO_DATE(T1.ATT_DATE, 'MM/DD/YYYY') DESC;

方案2:只在最新记录显示日期差(符合你的更新1期望输出)

用LAG()窗口函数直接获取同员工的上一条考勤日期,然后只保留最新的那条记录:

SELECT 
    T1.EMPNO AS Id,
    T1.ATT_DATE AS Date,
    TRUNC(
        TO_DATE(T1.ATT_DATE, 'MM/DD/YYYY') 
        - TO_DATE(T1.prev_att_date, 'MM/DD/YYYY')
    ) AS Days
FROM (
    SELECT 
        T2.EMPNO, 
        T2.ATT_DATE,
        ROW_NUMBER() OVER(PARTITION BY T2.EMPNO ORDER BY TO_DATE(T2.ATT_DATE, 'MM/DD/YYYY') DESC) AS rn,
        -- 获取同员工的上一条考勤日期
        LAG(T2.ATT_DATE) OVER(PARTITION BY T2.EMPNO ORDER BY TO_DATE(T2.ATT_DATE, 'MM/DD/YYYY') DESC) AS prev_att_date
    FROM TableName T2
) T1
WHERE T1.rn = 1 -- 只保留最新的考勤记录
  AND T1.prev_att_date IS NOT NULL; -- 确保存在上一条记录

关键注意点

  • 日期格式掩码:一定要在TO_DATE()里指定格式'MM/DD/YYYY',因为你的日期是1/24/2018这种月/日/年的格式,如果数据库默认格式不匹配,会导致日期解析错误,差值自然不对;
  • 窗口函数的分区与排序:所有窗口函数都要按EMPNO分区,按日期降序排序,这样才能精准匹配到同员工的相邻记录。

内容的提问来源于stack exchange,提问作者user8512043

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 04:23:46