0

残念ながら、これらのテーブルにインデックスを設定する権限がありません。

最初の 2 つWITH'sは、このクエリを何時間も実行する原因となっています。

;with OneAccession as (
select client_id,COUNT(patient_id) PatientCount from
(
select client_id,patient_id
from F_ACCESSION_DAILY
group by CLIENT_ID,PATIENT_ID
having COUNT(ACCESSION_ID)=1
) a
group by CLIENT_ID
)
,

TwoAccessions as (
select client_id,COUNT(patient_id) PatientCount from
(
select client_id,patient_id
from F_ACCESSION_DAILY
group by CLIENT_ID,PATIENT_ID
having COUNT(ACCESSION_ID)=2
) a
group by client_id
)



select
f.client_id
, 12*(year(getdate())-year(min(f.received_date))) + MONTH(GETDATE())-MONTH(min(f.received_date))
, COUNT(distinct f.patient_id) TotalPatients
, COUNT(f.ACCESSION_ID) TotalSpecimens
, o.PatientCount  TotalPatientsWOneSpec
, t.PatientCount TotalPatientsWTwoSpec
from F_ACCESSION_DAILY f
join
OneAccession o
on o.CLIENT_ID=f.CLIENT_ID
join
TwoAccessions t
on t.client_id=f.CLIENT_ID
where f.CLIENT_ID not in (select clientid from SalesDWH..TestPractices)
and f.SPECIMEN_SOURCE in ('Oral Fluid','Urine')
group by f.CLIENT_ID,o.PatientCount,t.PatientCount

と を削除するOneAccessionTwoAccessions、わずか数分で結果が得られます。

これを高速化するためにクエリ構文を改善するためのガイダンスに非常に感謝しています!

本当にありがとう。

4

2 に答える 2

4

2 つの group-by を実行するだけで、すべての結合を回避できます。最初にクライアント、患者ごとに標本を数えます。次に、クライアントごとにそれらのカウントを組み合わせます。

WITH SpecimenCountPerPatient AS(
  SELECT client_id, patient_id, COUNT(1) SpecimenCount, MIN(received_date) FirstSpecimenDate
  FROM dbo.F_ACCESSION_DAILY
  GROUP BY client_id, patient_id
)
SELECT client_id,
       DATEDIFF(Month,MIN(FirstSpecimenDate),GETDATE()) FirstSpecimenAgeInMonthForClient,
       COUNT(1) TotalPatients,
       SUM(SpecimenCount) TotalSpecimens,
       SUM(CASE WHEN SpecimenCount = 1 THEN 1 ELSE 0 END) TotalPatientsWOneSpec,
       SUM(CASE WHEN SpecimenCount = 2 THEN 1 ELSE 0 END) TotalPatientsWTwoSpec
FROM SpecimenCountPerPatient
GROUP BY client_id;

実際の動作を確認するための SQLFiddle を次に示します: http://sqlfiddle.com/#!3/72e40/2

さて、あなたがインデックスを追加できないと言ったのは知っていますが、client_id ASC、patient_id ASC INCLUDE(received_date) にインデックスを追加すると、処理がさらに高速化されます。

于 2012-10-16T13:00:39.413 に答える
2

これを試して、パフォーマンスが向上するかどうか教えてください

SELECT client_id,patient_id ,Accession_Id_Count = COUNT(ACCESSION_ID)
INTO #temp
from F_ACCESSION_DAILY 
group by CLIENT_ID,PATIENT_ID 

select 
f.client_id 
, 12*(year(getdate())-year(min(f.received_date))) + MONTH(GETDATE())-MONTH(min(f.received_date)) 
, COUNT(distinct f.patient_id) TotalPatients 
, COUNT(f.ACCESSION_ID) TotalSpecimens 
, o.PatientCount  TotalPatientsWOneSpec 
, t.PatientCount TotalPatientsWTwoSpec 
from F_ACCESSION_DAILY f 
join (select client_id,COUNT(patient_id) PatientCount from #temp where Accession_Id_Count = 1 group by CLIENT_ID ) o  on o.CLIENT_ID=f.CLIENT_ID 
join (select client_id,COUNT(patient_id) PatientCount from #temp where Accession_Id_Count = 2 group by CLIENT_ID ) t  on t.client_id=f.CLIENT_ID 
where f.CLIENT_ID not in (select clientid from SalesDWH..TestPractices) 
and f.SPECIMEN_SOURCE in ('Oral Fluid','Urine') 
group by f.CLIENT_ID,o.PatientCount,t.PatientCount 

drop table #temp
于 2012-10-16T03:28:17.867 に答える