如何使用T-SQL统计患者在诊所的连续签到次数
用T-SQL统计患者诊所签到次数(连续日期算一次)
我明白你要解决的问题:用T-SQL统计患者到诊所的签到次数,核心规则是同一患者在同一诊所的连续日期签到算作一次,非连续则算新的签到。这是典型的连续序列分组问题,咱们用窗口函数就能轻松搞定,下面是具体的实现方案:
假设的数据结构
首先假设你的签到表结构大概是这样的(如果实际结构不同,调整字段名即可):
CREATE TABLE PatientCheckins ( PatID INT, -- 患者ID PracticeID INT, -- 诊所ID CheckinDate DATE, -- 签到日期 -- 其他业务字段(如签到时间、状态等) );
核心实现代码
基础版本(默认同一天多次签到算多次,若需合并看下面的优化版)
WITH CheckinGroups AS ( SELECT PatID, PracticeID, CheckinDate, -- 生成签到组标识:首次签到或与上一次间隔超1天,就开启新组 SUM(CASE WHEN DATEDIFF(DAY, LAG(CheckinDate) OVER (PARTITION BY PatID, PracticeID ORDER BY CheckinDate), CheckinDate) > 1 OR LAG(CheckinDate) OVER (PARTITION BY PatID, PracticeID ORDER BY CheckinDate) IS NULL THEN 1 ELSE 0 END) OVER (PARTITION BY PatID, PracticeID ORDER BY CheckinDate) AS SignInGroupID FROM PatientCheckins ) -- 统计每个患者-诊所组合的签到次数 SELECT PatID, PracticeID, COUNT(DISTINCT SignInGroupID) AS TotalSignIns FROM CheckinGroups GROUP BY PatID, PracticeID ORDER BY PatID, PracticeID;
优化版本(同一天多次签到合并为一次)
如果患者同一天多次签到(比如当天进出多次),你想把这些算作一次签到的话,先对日期去重再分组:
WITH DistinctCheckins AS ( -- 先去重:同一患者同一诊所同一天只保留一条记录 SELECT DISTINCT PatID, PracticeID, CheckinDate FROM PatientCheckins ), CheckinGroups AS ( SELECT PatID, PracticeID, CheckinDate, SUM(CASE WHEN DATEDIFF(DAY, LAG(CheckinDate) OVER (PARTITION BY PatID, PracticeID ORDER BY CheckinDate), CheckinDate) > 1 OR LAG(CheckinDate) OVER (PARTITION BY PatID, PracticeID ORDER BY CheckinDate) IS NULL THEN 1 ELSE 0 END) OVER (PARTITION BY PatID, PracticeID ORDER BY CheckinDate) AS SignInGroupID FROM DistinctCheckins ) SELECT PatID, PracticeID, COUNT(DISTINCT SignInGroupID) AS TotalSignIns FROM CheckinGroups GROUP BY PatID, PracticeID ORDER BY PatID, PracticeID;
代码逻辑解释
- LAG函数:在每个
PatID+PracticeID的分组里,按签到日期排序,获取当前记录的上一条签到日期。 - 组标识生成:用
SUM窗口函数累加标记:如果当前日期和上一次签到日期间隔超过1天,或者是该患者该诊所的首次签到(上一次日期为NULL),就加1,这样连续日期的签到会被分到同一个SignInGroupID里。 - 统计次数:最后按
PatID+PracticeID分组,统计不同SignInGroupID的数量,就是该患者在该诊所的总签到次数。
内容的提问来源于stack exchange,提问作者FooBun
相关产品推荐
相关产品推荐

