[英]SQL : this query is taking too much of time
SQL :這個查詢花費了太多時間來處理 12 條記錄,還為表明智地創建了事件索引。
SELECT
p.AnchorDate,
'Active' StatusDefinition,
count(1) PatientCount,
6 AS SNO
FROM
(SELECT DISTINCT
pp.PatientID,
ad.AnchorDate
FROM
PatientProgram pp WITH (NOLOCK)
INNER JOIN
#tblMonth ad ON ad.AnchorDate = CASE
WHEN ad.AnchorDate BETWEEN DATEADD(dd, - (DAY(pp.EnrollmentStartDate) - 1), pp.EnrollmentStartDate)
AND EOMONTH (ISNULL(pp.EnrollmentEndDate, '9999-12-31'))
THEN ad.AnchorDate
ELSE NULL
END
WHERE NOT EXISTS (SELECT 1
FROM #ManagedPopulation m
WHERE m.tKeyId = pp.ProgramID)
AND pp.ProgramID != 4331) p
GROUP BY
p.AnchorDate;
CASE 在那里完全沒有價值。 您加入的ad.AnchorDate
與 CASE 的結果相等,但只有兩個選項,其中一個是 NULL,它永遠不會等於任何值(要查看某些內容是否為空,您需要使用 IS NULL),並且另一個是它自己。 因此,您可以輕松地使用日期之間的條件作為 JOIN 條件本身:
INNER JOIN #tblMonth ad
ON ad.AnchorDate BETWEEN
DATEADD(dd, - (DAY(pp.EnrollmentStartDate) - 1), pp.EnrollmentStartDate)
AND
EOMONTH (ISNULL(pp.EnrollmentEndDate, '9999-12-31'))
然后,您使用帶有 ISNULL 值的 BETWEEN 子句,您可以將其替換為 OR:
INNER JOIN #tblMonth ad
ON ad.AnchorDate >= DATEADD(dd, - (DAY(pp.EnrollmentStartDate) - 1), pp.EnrollmentStartDate)
AND
( pp.EnrollmentEndDate IS NULL OR ad.AnchorDate<=EOMONTH (pp.EnrollmentEndDate))
我在您的 where 條件中觀察到很少的文字。 在對大量數據庫運行查詢時,文字是主要的罪魁禍首。 快速測試是針對包含數百萬條記錄的數據庫運行原始查詢,並針對相同數據量運行修改后的查詢(用變量替換文字 - 下面給出的示例)。 您會觀察到性能的顯着差異。
WHEN ad.AnchorDate BETWEEN DATEADD(dd, - (DAY(pp.EnrollmentStartDate) - 1), pp.EnrollmentStartDate)
AND EOMONTH (ISNULL(pp.EnrollmentEndDate, '9999-12-31'))
如果您的查詢作為過程/函數的一部分存在,請聲明一個變量並分配值並將分配的值傳遞給 where 條件。
聲明@sp_Date DATETIME @sp_Date = GETDATE()
WHEN ad.AnchorDate BETWEEN DATEADD(dd, - (DAY(pp.EnrollmentStartDate) - 1), pp.EnrollmentStartDate)
AND EOMONTH (ISNULL(pp.EnrollmentEndDate, @sp_Date))
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.