SQL> explain plan for 2 SELECT gcc.segment1, 3 ffv1.DESCRIPTION, 4 gcc.segment3, 5 ffv3.DESCRIPTION, 6 gcc.segment2, 7 ffv2.DESCRIPTION, 8 gcc.segment4, 9 ffv4.DESCRIPTION, 10 gcc.segment5, 11 ffv5.DESCRIPTION, 12 gcc.segment6, 13 ffv6.DESCRIPTION, 14 gcc.segment7, 15 gbb.period_name, 16 gbb.period_net_dr - gbb.period_net_cr b_amount 17 FROM apps.gl_balances gbb, 18 apps.gl_code_combinations gcc, 19 apps.fnd_flex_values_vl ffv1, 20 apps.fnd_flex_values_vl ffv2, 21 apps.fnd_flex_values_vl ffv3, 22 apps.fnd_flex_values_vl ffv4, 23 apps.fnd_flex_values_vl ffv5, 24 apps.fnd_flex_values_vl ffv6, 25 apps.fnd_flex_value_sets ffvs1, 26 apps.fnd_flex_value_sets ffvs2, 27 apps.fnd_flex_value_sets ffvs3, 28 apps.fnd_flex_value_sets ffvs4, 29 apps.fnd_flex_value_sets ffvs5, 30 apps.fnd_flex_value_sets ffvs6 31 WHERE gbb.period_name = '2014-01' 32 /*WHERE gbb.period_name in 33 ('2014-01', '2014-02', '2014-03', '2013-04', '2013-05', '2013-06', 34 '2013-07', '2013-08', '2013-09', '2013-10', '2013-11', '2013-12')*/ 35 AND gbb.actual_flag = 'B' 36 AND gbb.template_id IS NULL 37 and gbb.currency_code = 'CNY' 38 and gbb.code_combination_id = gcc.code_combination_id 39 and ffv1.FLEX_VALUE = gcc.segment1 40 and ffv2.FLEX_VALUE = gcc.segment2 41 and ffv3.FLEX_VALUE = gcc.segment3 42 and ffv4.FLEX_VALUE = gcc.segment4 43 and ffv5.FLEX_VALUE = gcc.segment5 44 and ffv6.FLEX_VALUE = gcc.segment6 45 and ffv1.FLEX_VALUE_SET_ID = ffvs1.flex_value_set_id 46 and ffvs1.flex_value_set_name = 'JI_COA_COM' 47 and ffv2.FLEX_VALUE_SET_ID = ffvs2.flex_value_set_id 48 and ffvs2.flex_value_set_name = 'JI_COA_CST' 49 and ffv3.FLEX_VALUE_SET_ID = ffvs3.flex_value_set_id 50 and ffvs3.flex_value_set_name = 'JI_COA_ACC' 51 and ffv4.FLEX_VALUE_SET_ID = ffvs4.flex_value_set_id 52 and ffvs4.flex_value_set_name = 'JI_COA_BRD' 53 and ffv5.FLEX_VALUE_SET_ID = ffvs5.flex_value_set_id 54 and ffvs5.flex_value_set_name = 'JI_COA_PRJ' 55 and ffv6.FLEX_VALUE_SET_ID = ffvs6.flex_value_set_id 56 and ffvs6.flex_value_set_name = 'JI_COA_ICP' 57 and gbb.period_net_dr - gbb.period_net_cr <> 0 58 --and (gcc.segment1 in ('A06510', 'C00060') or gcc.segment1 like 'A6%') 59 --and gcc.segment1 in ('Z00010','Z00020') 60 --and (gcc.segment3 like '660201%'/* or gcc.segment3 like '660205%' or gcc.segment3 like '660207%' */) 61 order by 1, 3 62 ; Explained. SQL> set linesize 900 pagesize 900 SQL> select * from table(dbms_xplan.display); PLAN_TABLE_OUTPUT ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ ----------------------------------------------------------------------------------------------------------------- | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| ----------------------------------------------------------------------------------------------------------------- | 0 | SELECT STATEMENT | | 1 | 497 | 2138 (1)| | 1 | SORT ORDER BY | | 1 | 497 | 2138 (1)| | 2 | NESTED LOOPS | | | | | | 3 | NESTED LOOPS | | 1 | 497 | 2137 (1)| | 4 | NESTED LOOPS | | 1 | 474 | 2136 (1)| | 5 | NESTED LOOPS | | 1 | 454 | 2134 (1)| | 6 | NESTED LOOPS | | 1 | 431 | 2133 (1)| | 7 | NESTED LOOPS | | 1 | 411 | 2131 (1)| | 8 | NESTED LOOPS | | 1 | 388 | 2130 (1)| | 9 | NESTED LOOPS | | 1 | 368 | 2128 (1)| | 10 | NESTED LOOPS | | 1 | 345 | 2127 (1)| | 11 | NESTED LOOPS | | 1 | 325 | 2125 (1)| | 12 | NESTED LOOPS | | 1 | 302 | 2124 (1)| |* 13 | HASH JOIN | | 3 | 807 | 2114 (1)| | 14 | NESTED LOOPS | | | | | | 15 | NESTED LOOPS | | 1691 | 411K| 2027 (1)| |* 16 | HASH JOIN | | 48 | 10128 | 267 (3)| | 17 | TABLE ACCESS FULL | FND_FLEX_VALUES | 31095 | 607K| 86 (2)| | 18 | NESTED LOOPS | | 31088 | 5798K| 180 (3)| | 19 | NESTED LOOPS | | 1 | 168 | 7 (0)| | 20 | NESTED LOOPS | | 1 | 140 | 6 (0)| | 21 | NESTED LOOPS | | 1 | 112 | 5 (0)| | 22 | NESTED LOOPS | | 1 | 84 | 4 (0)| | 23 | NESTED LOOPS | | 1 | 56 | 3 (0)| | 24 | TABLE ACCESS BY INDEX ROWID| FND_FLEX_VALUE_SETS | 1 | 28 | 2 (0)| |* 25 | INDEX UNIQUE SCAN | FND_FLEX_VALUE_SETS_U2 | 1 | | 1 (0)| | 26 | TABLE ACCESS BY INDEX ROWID| FND_FLEX_VALUE_SETS | 1 | 28 | 1 (0)| |* 27 | INDEX UNIQUE SCAN | FND_FLEX_VALUE_SETS_U2 | 1 | | 0 (0)| | 28 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUE_SETS | 1 | 28 | 1 (0)| |* 29 | INDEX UNIQUE SCAN | FND_FLEX_VALUE_SETS_U2 | 1 | | 0 (0)| | 30 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUE_SETS | 1 | 28 | 1 (0)| |* 31 | INDEX UNIQUE SCAN | FND_FLEX_VALUE_SETS_U2 | 1 | | 0 (0)| | 32 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUE_SETS | 1 | 28 | 1 (0)| |* 33 | INDEX UNIQUE SCAN | FND_FLEX_VALUE_SETS_U2 | 1 | | 0 (0)| | 34 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUE_SETS | 1 | 28 | 1 (0)| |* 35 | INDEX UNIQUE SCAN | FND_FLEX_VALUE_SETS_U2 | 1 | | 0 (0)| |* 36 | TABLE ACCESS FULL | FND_FLEX_VALUES_TL | 31088 | 698K| 173 (3)| |* 37 | INDEX RANGE SCAN | IDX$$_104F60001 | 370 | | 3 (0)| | 38 | TABLE ACCESS BY INDEX ROWID | GL_CODE_COMBINATIONS | 36 | 1368 | 352 (0)| | 39 | TABLE ACCESS FULL | FND_FLEX_VALUES | 31095 | 607K| 86 (2)| |* 40 | TABLE ACCESS BY INDEX ROWID | GL_BALANCES | 1 | 33 | 4 (0)| |* 41 | INDEX RANGE SCAN | GL_BALANCES_N1 | 1 | | 2 (0)| | 42 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUES_TL | 1 | 23 | 1 (0)| |* 43 | INDEX UNIQUE SCAN | FND_FLEX_VALUES_TL_U1 | 1 | | 0 (0)| | 44 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUES | 1 | 20 | 2 (0)| |* 45 | INDEX RANGE SCAN | FND_FLEX_VALUES_N1 | 1 | | 1 (0)| | 46 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUES_TL | 1 | 23 | 1 (0)| |* 47 | INDEX UNIQUE SCAN | FND_FLEX_VALUES_TL_U1 | 1 | | 0 (0)| | 48 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUES | 1 | 20 | 2 (0)| |* 49 | INDEX RANGE SCAN | FND_FLEX_VALUES_N1 | 1 | | 1 (0)| | 50 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUES_TL | 1 | 23 | 1 (0)| |* 51 | INDEX UNIQUE SCAN | FND_FLEX_VALUES_TL_U1 | 1 | | 0 (0)| | 52 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUES | 1 | 20 | 2 (0)| |* 53 | INDEX RANGE SCAN | FND_FLEX_VALUES_N1 | 1 | | 1 (0)| | 54 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUES_TL | 1 | 23 | 1 (0)| |* 55 | INDEX UNIQUE SCAN | FND_FLEX_VALUES_TL_U1 | 1 | | 0 (0)| | 56 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUES | 1 | 20 | 2 (0)| |* 57 | INDEX RANGE SCAN | FND_FLEX_VALUES_N1 | 1 | | 1 (0)| |* 58 | INDEX UNIQUE SCAN | FND_FLEX_VALUES_TL_U1 | 1 | | 0 (0)| | 59 | TABLE ACCESS BY INDEX ROWID | FND_FLEX_VALUES_TL | 1 | 23 | 1 (0)| ----------------------------------------------------------------------------------------------------------------- Predicate Information (identified by operation id): --------------------------------------------------- 13 - access("B"."FLEX_VALUE"="GCC"."SEGMENT1" AND "B"."FLEX_VALUE_SET_ID"="FFVS1"."FLEX_VALUE_SET_ID") 16 - access("B"."FLEX_VALUE_SET_ID"="FFVS3"."FLEX_VALUE_SET_ID" AND "B"."FLEX_VALUE_ID"="T"."FLEX_VALUE_ID") 25 - access("FFVS6"."FLEX_VALUE_SET_NAME"='JI_COA_ICP') 27 - access("FFVS5"."FLEX_VALUE_SET_NAME"='JI_COA_PRJ') 29 - access("FFVS4"."FLEX_VALUE_SET_NAME"='JI_COA_BRD') 31 - access("FFVS3"."FLEX_VALUE_SET_NAME"='JI_COA_ACC') 33 - access("FFVS2"."FLEX_VALUE_SET_NAME"='JI_COA_CST') 35 - access("FFVS1"."FLEX_VALUE_SET_NAME"='JI_COA_COM') 36 - filter("T"."LANGUAGE"=USERENV('LANG')) 37 - access("B"."FLEX_VALUE"="GCC"."SEGMENT3") 40 - filter("GBB"."TEMPLATE_ID" IS NULL AND "GBB"."ACTUAL_FLAG"='B' AND "GBB"."CURRENCY_CODE"='CNY' AND "GBB"."PERIOD_NET_DR"-"GBB"."PERIOD_NET_CR"<>0) 41 - access("GBB"."CODE_COMBINATION_ID"="GCC"."CODE_COMBINATION_ID" AND "GBB"."PERIOD_NAME"='2014-01') 43 - access("B"."FLEX_VALUE_ID"="T"."FLEX_VALUE_ID" AND "T"."LANGUAGE"=USERENV('LANG')) 45 - access("B"."FLEX_VALUE_SET_ID"="FFVS2"."FLEX_VALUE_SET_ID" AND "B"."FLEX_VALUE"="GCC"."SEGMENT2") 47 - access("B"."FLEX_VALUE_ID"="T"."FLEX_VALUE_ID" AND "T"."LANGUAGE"=USERENV('LANG')) 49 - access("B"."FLEX_VALUE_SET_ID"="FFVS4"."FLEX_VALUE_SET_ID" AND "B"."FLEX_VALUE"="GCC"."SEGMENT4") 51 - access("B"."FLEX_VALUE_ID"="T"."FLEX_VALUE_ID" AND "T"."LANGUAGE"=USERENV('LANG')) 53 - access("B"."FLEX_VALUE_SET_ID"="FFVS5"."FLEX_VALUE_SET_ID" AND "B"."FLEX_VALUE"="GCC"."SEGMENT5") 55 - access("B"."FLEX_VALUE_ID"="T"."FLEX_VALUE_ID" AND "T"."LANGUAGE"=USERENV('LANG')) 57 - access("B"."FLEX_VALUE_SET_ID"="FFVS6"."FLEX_VALUE_SET_ID" AND "B"."FLEX_VALUE"="GCC"."SEGMENT6") 58 - access("B"."FLEX_VALUE_ID"="T"."FLEX_VALUE_ID" AND "T"."LANGUAGE"=USERENV('LANG')) Note ----- - 'PLAN_TABLE' is old version 96 rows selected.
问题是网友说这语句很慢,我想起以前另一个网友问过类似的问题。也是这种多次关联大数据,那见改写后没回复。
我问网友要不要试下我那次方法。
确认后开始改写。
因为改写的有点大,为了保证语句要先建立测试用表。
DROP TABLE apps.gl_code_combinations PURGE; CREATE TABLE apps.gl_code_combinations AS SELECT 1 AS segment1, 2 AS segment2, 3 AS segment3, 4 AS segment4, 5 AS segment5, 6 AS segment6, 7 AS segment7, 1 AS code_combination_id FROM dual; DROP TABLE apps.gl_balances PURGE; CREATE TABLE apps.gl_balances AS SELECT 2 AS period_net_dr, 1 AS period_net_cr, '2014-01' AS period_name, 'B' AS actual_flag, 'CNY' AS currency_code, 1 AS code_combination_id, 1 AS flex_value_set_id, 1 AS template_id FROM dual; UPDATE apps.gl_balances SET template_id = NULL; DROP TABLE apps.fnd_flex_values_vl PURGE; CREATE TABLE apps.fnd_flex_values_vl AS SELECT 1 AS flex_value,'a' AS DESCRIPTION,1 AS flex_value_set_id FROM dual UNION ALL SELECT 2 AS flex_value,'b' AS DESCRIPTION,1 AS flex_value_set_id FROM dual UNION ALL SELECT 3 AS flex_value,'c' AS DESCRIPTION,1 AS flex_value_set_id FROM dual UNION ALL SELECT 4 AS flex_value,'d' AS DESCRIPTION,1 AS flex_value_set_id FROM dual UNION ALL SELECT 5 AS flex_value,'e' AS DESCRIPTION,1 AS flex_value_set_id FROM dual UNION ALL SELECT 6 AS flex_value,'f' AS DESCRIPTION,1 AS flex_value_set_id FROM dual; DROP TABLE apps.fnd_flex_value_sets PURGE; CREATE TABLE apps.fnd_flex_value_sets AS SELECT 'JI_COA_COM' AS flex_value_set_name,1 AS flex_value_set_id FROM dual UNION ALL SELECT 'JI_COA_CST' AS flex_value_set_name,1 AS flex_value_set_id FROM dual UNION ALL SELECT 'JI_COA_ACC' AS flex_value_set_name,1 AS flex_value_set_id FROM dual UNION ALL SELECT 'JI_COA_BRD' AS flex_value_set_name,1 AS flex_value_set_id FROM dual UNION ALL SELECT 'JI_COA_PRJ' AS flex_value_set_name,1 AS flex_value_set_id FROM dual UNION ALL SELECT 'JI_COA_ICP' AS flex_value_set_name,1 AS flex_value_set_id FROM dual;
WITH gcc0 AS (SELECT rownum AS sn, gcc.segment1, gcc.segment2, gcc.segment3, gcc.segment4, gcc.segment5, gcc.segment6, gcc.segment7, gbb.period_name, gbb.period_net_dr - gbb.period_net_cr b_amount FROM apps.gl_balances gbb, apps.gl_code_combinations gcc WHERE gbb.period_name = '2014-01' AND gbb.actual_flag = 'B' AND gbb.template_id IS NULL AND gbb.currency_code = 'CNY' AND gbb.code_combination_id = gcc.code_combination_id AND gbb.period_net_dr <> gbb.period_net_cr), gcc AS (SELECT sn, 'JI_COA_COM' AS flex_value_set_name, segment1 AS segment0, segment7, period_name, b_amount FROM gcc0 UNION ALL SELECT sn, 'JI_COA_CST' AS flex_value_set_name, segment2 AS segment0, segment7, period_name, b_amount FROM gcc0 UNION ALL SELECT sn, 'JI_COA_ACC' AS flex_value_set_name, segment3 AS segment0, segment7, period_name, b_amount FROM gcc0 UNION ALL SELECT sn, 'JI_COA_BRD' AS flex_value_set_name, segment4 AS segment0, segment7, period_name, b_amount FROM gcc0 UNION ALL SELECT sn, 'JI_COA_PRJ' AS flex_value_set_name, segment5 AS segment0, segment7, period_name, b_amount FROM gcc0 UNION ALL SELECT sn, 'JI_COA_ICP' AS flex_value_set_name, segment6 AS segment0, segment7, period_name, b_amount FROM gcc0) SELECT MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_COM' THEN gcc.segment0 END) AS segment1, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_CST' THEN gcc.segment0 END) AS segment1, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_ACC' THEN gcc.segment0 END) AS segment1, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_BRD' THEN gcc.segment0 END) AS segment1, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_PRJ' THEN gcc.segment0 END) AS segment1, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_ICP' THEN gcc.segment0 END) AS segment1, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_COM' THEN ffv.description END) AS des1, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_CST' THEN ffv.description END) AS des2, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_ACC' THEN ffv.description END) AS des3, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_BRD' THEN ffv.description END) AS des4, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_PRJ' THEN ffv.description END) AS des5, MAX(CASE gcc.flex_value_set_name WHEN 'JI_COA_ICP' THEN ffv.description END) AS des6, MAX(gcc.segment7) AS segment7, MAX(gcc.segment7) AS segment7 FROM gcc, apps.fnd_flex_values_vl ffv, apps.fnd_flex_value_sets ffvs WHERE ffv.flex_value = gcc.segment0 AND ffv.flex_value_set_id = ffvs.flex_value_set_id AND ffvs.flex_value_set_name = gcc.flex_value_set_name GROUP BY gcc.sn HAVING COUNT (*) = 6
先把固定表数据作了列转行,几个字段放在了同一行中,然后再与view关联一次就够了。
取数据后恢复为一行。改写完时原查询还没执行完(已执行了20分钟了,据说原来要10分钟)。
试下这个改写后的吧。
11:57:28
下面是改写后的plan
SQL> select * from table(dbms_xplan.display); PLAN_TABLE_OUTPUT ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ ---------------------------------------------------------------------------------------------------- | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| ---------------------------------------------------------------------------------------------------- | 0 | SELECT STATEMENT | | 4 | 496 | 13314 (1)| | 1 | TEMP TABLE TRANSFORMATION | | | | | | 2 | LOAD AS SELECT | FND_FLEX_VALUE_SETS | | | | | 3 | COUNT | | | | | |* 4 | HASH JOIN | | 9556 | 662K| 12975 (1)| |* 5 | TABLE ACCESS BY INDEX ROWID| GL_BALANCES | 9556 | 307K| 9296 (1)| |* 6 | INDEX RANGE SCAN | GL_BALANCES_N2 | 334K| | 1480 (1)| | 7 | TABLE ACCESS FULL | GL_CODE_COMBINATIONS | 890K| 32M| 3670 (2)| |* 8 | FILTER | | | | | | 9 | HASH GROUP BY | | 4 | 496 | 339 (3)| | 10 | NESTED LOOPS | | | | | | 11 | NESTED LOOPS | | 4 | 496 | 338 (2)| |* 12 | HASH JOIN | | 4 | 404 | 334 (2)| |* 13 | HASH JOIN | | 31095 | 1457K| 168 (2)| | 14 | TABLE ACCESS FULL | FND_FLEX_VALUE_SETS | 16637 | 454K| 81 (0)| | 15 | TABLE ACCESS FULL | FND_FLEX_VALUES | 31095 | 607K| 86 (2)| | 16 | VIEW | | 57336 | 2967K| 164 (2)| | 17 | UNION-ALL | | | | | | 18 | VIEW | | 9556 | 382K| 27 (0)| | 19 | TABLE ACCESS FULL | SYS_TEMP_0FD9D6621_12726068 | 9556 | 625K| 27 (0)| | 20 | VIEW | | 9556 | 382K| 27 (0)| | 21 | TABLE ACCESS FULL | SYS_TEMP_0FD9D6621_12726068 | 9556 | 625K| 27 (0)| | 22 | VIEW | | 9556 | 382K| 27 (0)| | 23 | TABLE ACCESS FULL | SYS_TEMP_0FD9D6621_12726068 | 9556 | 625K| 27 (0)| | 24 | VIEW | | 9556 | 382K| 27 (0)| | 25 | TABLE ACCESS FULL | SYS_TEMP_0FD9D6621_12726068 | 9556 | 625K| 27 (0)| | 26 | VIEW | | 9556 | 382K| 27 (0)| | 27 | TABLE ACCESS FULL | SYS_TEMP_0FD9D6621_12726068 | 9556 | 625K| 27 (0)| | 28 | VIEW | | 9556 | 382K| 27 (0)| | 29 | TABLE ACCESS FULL | SYS_TEMP_0FD9D6621_12726068 | 9556 | 625K| 27 (0)| |* 30 | INDEX UNIQUE SCAN | FND_FLEX_VALUES_TL_U1 | 1 | | 0 (0)| | 31 | TABLE ACCESS BY INDEX ROWID| FND_FLEX_VALUES_TL | 1 | 23 | 1 (0)| ---------------------------------------------------------------------------------------------------- Predicate Information (identified by operation id): --------------------------------------------------- 4 - access("GBB"."CODE_COMBINATION_ID"="GCC"."CODE_COMBINATION_ID") 5 - filter("GBB"."TEMPLATE_ID" IS NULL AND "GBB"."ACTUAL_FLAG"='B' AND "GBB"."CURRENCY_CODE"='CNY' AND "GBB"."PERIOD_NET_DR"<>"GBB"."PERIOD_NET_CR") 6 - access("GBB"."PERIOD_NAME"='2014-01') 8 - filter(COUNT(*)=6) 12 - access("B"."FLEX_VALUE"="GCC"."SEGMENT0" AND "FFVS"."FLEX_VALUE_SET_NAME"="GCC"."FLEX_VALUE_SET_NAME") 13 - access("B"."FLEX_VALUE_SET_ID"="FFVS"."FLEX_VALUE_SET_ID") 30 - access("B"."FLEX_VALUE_ID"="T"."FLEX_VALUE_ID" AND "T"."LANGUAGE"=USERENV('LANG')) Note ----- - 'PLAN_TABLE' is old version 54 rows selected.
是不是要清爽些,哈哈
原语句也可以不改写,直接加hint改plan,把nl转为hash