Reputation: 447
I have got a query like below, executing in SQL Server 2008
SELECT
ipm.HEORG_REFNO,
ipm.HOTYP_REFNO,
ipm.CASLT_REFNO,
ipm.HOLVL_REFNO,
IPM.MAIN_IDENT,
...
FROM
dbo.HEALTH_ORGANISATIONS ipm (NOLOCK)
LEFT JOIN
(SELECT
s.heorg_refno, min(s.start_dttm) as start_dttm_SPONT, max(isnull(convert(datetime,s.end_dttm,120),convert(datetime,'9999-01-01', 120))) as end_dttm_SPONT
FROM
dbo.service_points s (NOLOCK)
INNER JOIN
dbo.reference_values rfval (NOLOCK) ON s.SPTYP_REFNO = rfval.RFVAL_REFNO
AND RFVAL.MAIN_CODE != 'PDT'
GROUP BY
s.heorg_refno) SPONT ON ipm.HEORG_REFNO = SPONT.HEORG_REFNO
-- Bring only Health Organisation records and also certain records,whose HOTYP_REFNO does not exist in REF_VALS
WHERE
NOT EXISTS ((SELECT 'x'
FROM REFERENCE_VALUES RVAL (NOLOCK)
WHERE RVAL.RFVAL_REFNO = ipm.HOTYP_REFNO
AND main_code IN ('011','012','015','016', '017','019','2','AANDE','AEB','AEC','CLINIC','DAYCC','DEPRT','GPSIT','HC','HOSPL','HOST','LOCTN','LOSYN','MIU','MISC','MRL', 'SITE','THEAT','WARD','PDT','NURHM','DAYCR')
or ipm.HEORG_REFNO IN(select distinct HEORG_REFNO from SERVICE_POINT_SESSIONS (NOLOCK) where OWNER_HEORG_REFNO = 2001934 and HEORG_REFNO != 2001934)
or ipm.HEORG_REFNO IN (select REFNO from LOR_IPM_SYNTH_STG_DEV.. STAGING_Activity_LOCATION_DCS (NOLOCK) where Sources='HEORG_REFNO' and REFNO != 2001934)
)
)
It takes hell a lot of time to execute the query .
When I comment the below 2 lines, it runs faster:
or ipm.HEORG_REFNO IN(select distinct HEORG_REFNO from SERVICE_POINT_SESSIONS (NOLOCK) where OWNER_HEORG_REFNO = 2001934 and HEORG_REFNO != 2001934)
or ipm.HEORG_REFNO IN (select REFNO from LOR_IPM_SYNTH_STG_DEV.. STAGING_Activity_LOCATION_DCS (NOLOCK) where Sources='HEORG_REFNO' and REFNO != 2001934)
Thanks for any guidance provided in tuning the query
Upvotes: 2
Views: 90
Reputation: 77876
Try converting those IN
subquery to a JOIN
query like below and make sure you have proper index created on all the columns involved in join condition and where filter condition.
LEFT JOIN SERVICE_POINT_SESSIONS sps ON ipm.HEORG_REFNO = sps.HEORG_REFNO
AND sps.OWNER_HEORG_REFNO = 2001934
AND sps.HEORG_REFNO != 2001934
I would modify your query to be like below. Though I can't do nothing about your big inlist as of now but you should pull that inlist in a table variable and consider doing a JOIN
with that rather.
SELECT
ipm.HEORG_REFNO,
ipm.HOTYP_REFNO,
ipm.CASLT_REFNO,
ipm.HOLVL_REFNO,
IPM.MAIN_IDENT,
...
FROM
dbo.HEALTH_ORGANISATIONS ipm
LEFT JOIN
(SELECT
s.heorg_refno, min(s.start_dttm) as start_dttm_SPONT,
max(isnull(convert(datetime,s.end_dttm,120),convert(datetime,'9999-01-01', 120))) as end_dttm_SPONT
FROM
dbo.service_points s
INNER JOIN dbo.reference_values rfval
ON s.SPTYP_REFNO = rfval.RFVAL_REFNO
AND RFVAL.MAIN_CODE != 'PDT'
GROUP BY
s.heorg_refno) SPONT ON ipm.HEORG_REFNO = SPONT.HEORG_REFNO
LEFT JOIN SERVICE_POINT_SESSIONS sps
ON ipm.HEORG_REFNO = sps.HEORG_REFNO
AND sps.OWNER_HEORG_REFNO = 2001934
AND sps.HEORG_REFNO != 2001934
LEFT JOIN LOR_IPM_SYNTH_STG_DEV .. STAGING_Activity_LOCATION_DCS sald
ON ipm.HEORG_REFNO = sald.HEORG_REFNO
AND sald.Sources='HEORG_REFNO'
AND sald.REFNO != 2001934
WHERE NOT EXISTS (SELECT 1
FROM REFERENCE_VALUES RVAL
WHERE RVAL.RFVAL_REFNO = ipm.HOTYP_REFNO
AND RVAL.main_code IN ('011','012','015','016', '017','019','2','AANDE','AEB','AEC','CLINIC','DAYCC','DEPRT','GPSIT','HC','HOSPL','HOST','LOCTN','LOSYN','MIU','MISC','MRL', 'SITE','THEAT','WARD','PDT','NURHM','DAYCR'));
Upvotes: 1
Reputation: 6390
My first thoughts are that your query is massively complex - I would be looking at ways to simplify it...
In clauses don't always perform well - I would be tempted to suck this info into a table variable of banned "main_Codes", left join to it and test for null...
Time to run the Execution Plan though and see where your bottle necks actually are, which will depend on your own environment (indexing, stats etc)...
Upvotes: 2