Avec tout le respect que je vous dois et à mon humble avis,
There is not much difference between While LOOP and Recursive CTE in terms of RBAR
Il n'y a pas beaucoup de gain de performances lors de l'utilisation Recursive CTE
et Window Partition function
tout en un.
Appid
devrait être int identity(1,1)
, ou il devrait être en constante augmentation clustered index
.
Outre d'autres avantages, il garantit également que toutes les rangées successives APPDate
de ce patient doivent être plus grandes.
De cette façon, vous pouvez facilement jouer avec APPID
votre requête, ce qui sera plus efficace que de mettre un inequality
opérateur comme>, <dans APPDate. Mettre l' inequality
opérateur comme>, <dans APPID aidera Sql Optimizer.
Il devrait également y avoir deux colonnes de date dans le tableau comme
APPDateTime datetime2(0) not null,
Appdate date not null
Comme ce sont les colonnes les plus importantes du tableau le plus important, donc pas beaucoup de conversion, convertissez.
Non clustered index
Peut donc être créé sur Appdate
Create NonClustered index ix_PID_AppDate_App on APP (patientid,APPDate) include(other column which is not i predicate except APPID)
Testez mon script avec d'autres exemples de données et laissez-moi savoir pour quels exemples de données il ne fonctionne pas. Même si cela ne fonctionne pas, je suis sûr qu'il peut être corrigé dans ma logique de script elle-même.
CREATE TABLE #Appt1 (ApptID INT, PatientID INT, ApptDate DATE)
INSERT INTO #Appt1
SELECT 1,101,'2020-01-05' UNION ALL
SELECT 2,505,'2020-01-06' UNION ALL
SELECT 3,505,'2020-01-10' UNION ALL
SELECT 4,505,'2020-01-20' UNION ALL
SELECT 5,101,'2020-01-25' UNION ALL
SELECT 6,101,'2020-02-12' UNION ALL
SELECT 7,101,'2020-02-20' UNION ALL
SELECT 8,101,'2020-03-30' UNION ALL
SELECT 9,303,'2020-01-28' UNION ALL
SELECT 10,303,'2020-02-02'
;With CTE as
(
select a1.* ,a2.ApptDate as NewApptDate
from #Appt1 a1
outer apply(select top 1 a2.ApptID ,a2.ApptDate
from #Appt1 A2
where a1.PatientID=a2.PatientID and a1.ApptID>a2.ApptID
and DATEDIFF(day,a2.ApptDate, a1.ApptDate)>30
order by a2.ApptID desc )A2
)
,CTE1 as
(
select a1.*, a2.ApptDate as FollowApptDate
from CTE A1
outer apply(select top 1 a2.ApptID ,a2.ApptDate
from #Appt1 A2
where a1.PatientID=a2.PatientID and a1.ApptID>a2.ApptID
and DATEDIFF(day,a2.ApptDate, a1.ApptDate)<=30
order by a2.ApptID desc )A2
)
select *
,case when FollowApptDate is null then 'New'
when NewApptDate is not null and FollowApptDate is not null
and DATEDIFF(day,NewApptDate, FollowApptDate)<=30 then 'New'
else 'Followup' end
as Category
from cte1 a1
order by a1.PatientID
drop table #Appt1