我有如下查询:
SELECT col1,col2,col3,col4,col5,unit1,unit2,unit3,unit4,unit5
FROM (select x.*,
to_number(substr(it_specs,instr(it_specs,',',1,1)+1,instr(it_specs,',',1,2)-instr(it_specs,',',1,1)-1)) unit1,
to_number(substr(it_specs,instr(it_specs,',',1,2)+1,instr(it_specs,',',1,3)-instr(it_specs,',',1,2)-1)) unit2,
to_number(substr(it_specs,instr(it_specs,',',1,3)+1,instr(it_specs,',',1,4)-instr(it_specs,',',1,3)-1)) unit3,
to_number(substr(it_specs,instr(it_specs,',',1,4)+1,instr(it_specs,',',1,5)-instr(it_specs,',',1,4)-1)) unit4,
to_number(substr(it_specs,instr(it_specs,',',1,5)+1,instr(it_specs,',',1,6)-instr(it_specs,',',1,5)-1)) unit5
from (select a.*,
(select IT_PKG.IT_SPECS(charges, TRUNC(usrdate), 'N')
from dual) AS it_Specs
from tabl1 A
ORDER BY a.col1, a.col2, a.col3, a.col4, a.col5) x) a,
tabl2 B
WHERE A.CA = B.CA
group by col1, col2, col3, col4, col5,
unit1, unit2, unit3, unit4, unit5
记录数量tabl1的范围是100到25000.tabl2中的记录数是一千。 函数IT_SPECS涉及两个表。每个都有50万条记录。 这个查询工作正常几个月没有性能问题。从下面的轨迹可以看出:
call count cpu elapsed disk query current rows
------- ------ -------- ---------- ---------- ---------- ---------- ----------
Parse 1 0.00 0.00 0 0 0 0
Execute 1 0.01 0.01 0 2 0 0
Fetch 6177 0.90 1.04 375 761 0 12351
------- ------ -------- ---------- ---------- ---------- ---------- ----------
total 6179 0.92 1.06 375 763 0 12351
但表现无明显下降。
call count cpu elapsed disk query current rows
------- ------ -------- ---------- ---------- ---------- ---------- ----------
Parse 1 0.02 0.03 0 0 0 0
Execute 1 0.02 0.10 239 153 0 0
Fetch 107 5.58 26.54 680 70660 0 10637
------- ------ -------- ---------- ---------- ---------- ---------- ----------
total 109 5.64 26.67 919 70813 0 10637
我的问题为什么我获得高查询值和经过的时间也很高? 获取计数是第二种情况,但它对性能没有影响。
解释计划:
执行查询时计划:
Rows (1st) Rows (avg) Rows (max) Row Source Operation
---------- ---------- ---------- ---------------------------------------------------
11030 11030 11030 FAST DUAL (cr=0 pr=0 pw=0 time=9295 us cost=2 size=0 card=1)
12300 12300 12300 HASH GROUP BY (cr=774 pr=375 pw=375 time=738182 us cost=216 size=2290 card=2)
12613 12613 12613 HASH JOIN (cr=774 pr=0 pw=0 time=545344 us cost=215 size=14622795 card=12771)
13 13 13 VIEW index$_join$_005 (cr=6 pr=0 pw=0 time=2267 us cost=3 size=104 card=13)
13 13 13 HASH JOIN (cr=6 pr=0 pw=0 time=2254 us)
13 13 13 INDEX FAST FULL SCAN C_TYP_UK1 (cr=3 pr=0 pw=0 time=68 us cost=1 size=104 card=13)(object id 81097)
13 13 13 INDEX FAST FULL SCAN C_TYP_X1 (cr=3 pr=0 pw=0 time=51 us cost=1 size=104 card=13)(object id 390320)
12613 12613 12613 VIEW (cr=768 pr=0 pw=0 time=520833 us cost=211 size=14520627 card=12771)
12613 12613 12613 TABLE ACCESS FULL tabl1 (cr=752 pr=0 pw=0 time=43361 us cost=211 size=13779909 card=12771)
********************************************************************************
计划何时出现性能问题:
Rows (1st) Rows (avg) Rows (max) Row Source Operation
---------- ---------- ---------- ---------------------------------------------------
13676 13676 13676 FAST DUAL (cr=0 pr=0 pw=0 time=26975 us cost=2 size=0 card=1)
13754 13754 13754 HASH GROUP BY (cr=109351 pr=1072 pw=435 time=31552012 us cost=273 size=2290 card=2)
15875 15875 15875 HASH JOIN (cr=109351 pr=637 pw=0 time=37695338 us cost=271 size=20364970 card=17786)
13 13 13 VIEW index$_join$_005 (cr=6 pr=0 pw=0 time=5159 us cost=3 size=104 card=13)
13 13 13 HASH JOIN (cr=6 pr=0 pw=0 time=5142 us)
13 13 13 INDEX FAST FULL SCAN C_TYP_UK1 (cr=3 pr=0 pw=0 time=175 us cost=1 size=104 card=13)(object id 81097)
13 13 13 INDEX FAST FULL SCAN C_TYP_X1 (cr=3 pr=0 pw=0 time=152 us cost=1 size=104 card=13)(object id 390320)
15875 15875 15875 VIEW (cr=109345 pr=637 pw=0 time=37587033 us cost=268 size=20222682 card=17786)
15875 15875 15875 TABLE ACCESS FULL tabl1 (cr=952 pr=632 pw=0 time=50917 us cost=268 size=19191094 card=17786)
********************************************************************************
此查询在数月内运行良好。实际上我更感兴趣的是知道为什么几个月后性能下降以及为什么我们获得高查询价值?
答案 0 :(得分:0)
你知道早些时候执行的执行计划吗? 首先,收集相关表的表统计信息。
请勿使用(select IT_PKG.IT_SPECS(charges, TRUNC(usrdate), 'N') from dual) AS it_Specs
,只需执行IT_PKG.IT_SPECS(charges, TRUNC(usrdate), 'N') AS it_Specs
。
<强>更新强> 此查询现在是否返回所需的结果?
WITH x AS
(SELECT ca,col1,col2,col3,col4,col5,IT_PKG.IT_SPECS(charges, TRUNC(usrdate), 'N') AS it_Specs
FROM tabl1)
a AS
(SELECT x.*,
TO_NUMBER(SUBSTR(it_specs,INSTR(it_specs,',',1,1)+1,INSTR(it_specs,',',1,2)-INSTR(it_specs,',',1,1)-1)) unit
FROM x)
SELECT a.*,
unit AS unit1, unit AS unit2, unit AS unit3, unit AS unit4, unit AS unit5 -- always the same
FROM a
JOIN tabl2 B ON A.CA = B.CA
GROUP BY col1,col2,col3,col4,col5,unit1,unit2,unit3,unit4,unit5
ORDER BY col1,col2,col3,col4,col5
答案 1 :(得分:0)
我已经看到了Oracle在很多次重复函数调用的一些问题,即使它只是&#39;只是&#39;来自dual
的选择。
尝试将查询移至with
。请参阅this。