我有一个相当大的SQL查询,其中大部分来自Business Objects SQL导出,必须在SQL Server上复制才能进行报告。
视图现在已经完成并且运行但是由于大量的子句很快填满了tempdb而且已经崩溃。
据我所知,我需要WHERE子句中的所有内容,但我觉得这可以优化以不填充tempdb。
其中的条款如下:
WHERE
dbo.VIEW1.ABSENCE_TYPE IN ('leavetype1', 'leavetype2', 'leavetype3', 'leavetype4', 'leavetype5')
AND
(
(ALIAS1.link_type_id='PN_RP_UNIT' or ALIAS1.link_type_id IS NULL) )
AND ( ALIAS2.OBJECT_TYPE='POSITION' )
AND ( ALIAS3.object_type='UNIT' )
AND ( CONTRACT_NAME.object_type='CONT' )
AND ( (POST_LNK.link_type_id='POSITION' OR POST_LNK.link_type_id IS NULL) )
AND ( dbo.table1.link_type_id = 'CONT' )
AND ( dbo.table1.team_party_id IS NULL )
AND ( EMP_TPERSON.non_emp_s='0' )
--AND (( ( dbo.tleaver.starting_d ) <= @Prompt('Report To Date','D',,Mono,Free) AND (( dbo.tleaver.leaving_d ) >= @Prompt('Report From Date','D',,Mono,Free) OR ( dbo.tleaver.leaving_d ) is null) )
AND dbo.VIEW4.UNIT_NM_01 = 'Orgainisation Name'
AND ALIAS2.PARTY_NM NOT LIKE '%occ1%'
AND ALIAS2.PARTY_NM NOT LIKE '%occ2%'
AND dbo.VIEW2.CONTRACTUAL_HOURS != 0
AND dbo.VIEW6.FTE_HOURS != 0
AND ( (ALIAS1.PARTY_LNK_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR ALIAS1.PARTY_LNK_D IS NULL) AND (ALIAS1.PARTY_LNK_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR ALIAS1.PARTY_LNK_ED IS NULL) )
AND ( (( dbo.table1.PARTY_LNK_D ) <= ( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.table1.PARTY_LNK_D ) is null) AND (( dbo.table1.PARTY_LNK_ED ) >= ( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.table1.PARTY_LNK_ED ) is null) )
--AND dbo.VIEW1.ABSENCE_START_DATE <= @variable('report to date')
--AND (dbo.VIEW1.ABSENCE_END_DATE >= @variable('report from date')
-- OR dbo.VIEW1.ABSENCE_END_DATE IS NULL )
--AND dbo.VIEW3.ABS_DAY_DATE >= @variable('report from date')
--AND dbo.VIEW3.ABS_DAY_DATE <= @variable('report to date')
AND ( (POST_LNK.PARTY_LNK_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR POST_LNK.PARTY_LNK_D is null) AND (POST_LNK.PARTY_LNK_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR POST_LNK.PARTY_LNK_ED is null) )
AND ( (dbo.VIEW2.INHERITED_FROM_DATE<=( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW2.INHERITED_FROM_DATE IS NULL) AND (dbo.VIEW2.INHERITED_TO_DATE>=( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW2.INHERITED_TO_DATE IS NULL) AND (dbo.VIEW2.HOURS_START_DATE<=( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW2.HOURS_START_DATE IS NULL) AND (dbo.VIEW2.HOURS_END_DATE>=( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW2.HOURS_END_DATE IS NULL) )
AND ( (dbo.VIEW6.INHERITED_FROM_DATE<=( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW6.INHERITED_FROM_DATE IS NULL) AND (dbo.VIEW6.INHERITED_TO_DATE>=( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW6.INHERITED_TO_DATE IS NULL) AND (dbo.VIEW6.HOURS_START_DATE<=( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW6.HOURS_START_DATE IS NULL) AND (dbo.VIEW6.HOURS_END_DATE>=( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW6.HOURS_END_DATE IS NULL) )
AND ( (dbo.VIEW4.LNK_01_02_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_01_02_D IS NULL) AND (dbo.VIEW4.LNK_02_03_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_02_03_D IS NULL) AND (dbo.VIEW4.LNK_03_04_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_03_04_D IS NULL) AND (dbo.VIEW4.LNK_04_05_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_04_05_D IS NULL) AND (dbo.VIEW4.LNK_05_06_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_05_06_D IS NULL) AND (dbo.VIEW4.LNK_06_07_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_06_07_D IS NULL) AND (dbo.VIEW4.LNK_07_08_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_07_08_D IS NULL) AND (dbo.VIEW4.LNK_08_09_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_08_09_D IS NULL) AND (dbo.VIEW4.LNK_09_10_D <= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_09_10_D IS NULL) AND (dbo.VIEW4.LNK_01_02_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_01_02_ED IS NULL) AND (dbo.VIEW4.LNK_02_03_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_02_03_ED IS NULL) AND (dbo.VIEW4.LNK_03_04_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_03_04_ED IS NULL) AND (dbo.VIEW4.LNK_04_05_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_04_05_ED IS NULL) AND (dbo.VIEW4.LNK_05_06_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_05_06_ED IS NULL) AND (dbo.VIEW4.LNK_06_07_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_06_07_ED IS NULL) AND (dbo.VIEW4.LNK_07_08_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_07_08_ED IS NULL) AND (dbo.VIEW4.LNK_08_09_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_08_09_ED IS NULL) AND (dbo.VIEW4.LNK_09_10_ED >= ( dbo.VIEW3.ABS_DAY_DATE ) OR dbo.VIEW4.LNK_09_10_ED IS NULL) )
AND ALIAS2.PARTY_NM NOT LIKE 'pos1'
AND dbo.VIEW5.contract_category IN ('pos2', 'pos3', 'pos4', 'pos4')
AND ( (( dbo.VIEW5.inherited_from_date )<=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW5.inherited_from_date ) IS NULL) AND (( dbo.VIEW5.inherited_to_date )>=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW5.inherited_to_date ) IS NULL) AND (( dbo.VIEW5.contract_category_d )<=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW5.contract_category_d ) IS NULL) AND (( dbo.VIEW5.contract_category_ed )>=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW5.contract_category_ed ) IS NULL) )
AND ALIAS2.PARTY_NM NOT LIKE 'role1'
AND ALIAS2.PARTY_NM NOT LIKE 'role2'
AND ALIAS2.PARTY_NM NOT LIKE '%role3%'
AND ( (( dbo.VIEW4.inherited_from_date )<=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW4.inherited_from_date ) IS NULL) AND (( dbo.VIEW4.inherited_to_date )>=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW4.inherited_to_date ) IS NULL) AND (( dbo.VIEW4.contract_basis_d )<=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW4.contract_basis_d ) IS NULL) AND (( dbo.VIEW4.contract_basis_ed )>=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW4.contract_basis_ed ) IS NULL) )
AND dbo.VIEW5.contract_category IN ('pos1', 'pos2', 'pos3', 'pos4')
AND ( (( dbo.VIEW5.inherited_from_date )<=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW5.inherited_from_date ) IS NULL) AND (( dbo.VIEW5.inherited_to_date )>=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW5.inherited_to_date ) IS NULL) AND (( dbo.VIEW5.contract_category_d )<=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW5.contract_category_d ) IS NULL) AND (( dbo.VIEW5.contract_category_ed )>=( dbo.VIEW3.ABS_DAY_DATE ) OR ( dbo.VIEW5.contract_category_ed ) IS NULL)
Onece运行这应该可以带回大约50,000行数据,任何人都可以就如何停止对tempdb施加如此大的压力并运行此查询提出任何建议。
答案 0 :(得分:4)
所有结构都是这样的:
(POST_LNK.link_type_id='POSITION' OR POST_LNK.link_type_id IS NULL)
可以重新计算到
ISNULL(POST_LNK.link_type_id,'POSITION') = 'POSITION'
仅仅因为where子句是“减速”并不意味着在查询的其余部分中不会发生重新分解。通常,连接和子查询可以被修改为具有约束并且提供巨大的速度提升,因为外部查询检查的记录较少。
另外,如果我要接受WAG,我会说你的问题在于像这样的元素:
AND ALIAS2.PARTY_NM NOT LIKE '%occ1%'
AND ALIAS2.PARTY_NM NOT LIKE '%occ2%'
AND ALIAS2.PARTY_NM NOT LIKE '%role3%'
如果是问题,您可以考虑重新分解以删除此部分(例如,添加occ
布尔列并在插入和修改时更新它。)
我还注意到你正在加入一些视图,如果视图正在做一些像执行函数调用那样愚蠢的事情,这可能是个问题。如果没有使用列,SQL可能会优化这些减速,但如果您在where中使用该元素,则重新添加它们。