WITH AS and materialize hints

来源:互联网 发布:淘宝 消防工程师教材 编辑:程序博客网 时间:2024/06/06 03:40

FROM http://blog.csdn.net/zhaoyangjian724/article/details/17692199?ADUIN=604178834&ADSESSION=1388405668&ADTAG=CLIENT.QQ.5281_.0&ADPUBNO=26283


  1. WITH AS: 就是将一个子查询部分独立出来,有时候是为了提高SQL语句的可读性,有时候是为了提高SQL语句性能。  
  2.           如果一个SQL语句中,某个表会被访问多次,而且每次访问的限制条件一样的话,就可以使用with as来提高性能。  
  3.           注意:如果 with as 短语没有被调用2次以上,CBO就不会讲这个短语获取的数据放入temp表,如果想要讲数据放入temp表需要使用materialize hint  
  4.                 如果 with as 短语被调用了2次以上,CBO会自动将 with as 短语的数据放入一个临时表,这个时候不用写materialize hint  
  5.   
  6.   
  7.   
  8. 举个例子(本例基于Scott用户)  
  9.   
  10. SQL> explain plan for  
  11. with a as (select /*+ materialize */ ename,job,deptno from emp where sal>(select avg(sal) from emp))  
  12. select * from a ;  
  13.   2    3  
  14. Explained.  
  15.   
  16. SQL> select * from table(dbms_xplan.display);  
  17.   
  18. PLAN_TABLE_OUTPUT  
  19. -------------------------------------------------------------------------------------------------------  
  20. Plan hash value: 2006423466  
  21.   
  22. -------------------------------------------------------------------------------------------------------  
  23. | Id  | Operation                  | Name                     | Rows  | Bytes | Cost (%CPU)| Time     |  
  24. -------------------------------------------------------------------------------------------------------  
  25. |   0 | SELECT STATEMENT           |                          |     1 |    26 |     8   (0)| 00:00:01 |  
  26. |   1 |  TEMP TABLE TRANSFORMATION |                          |       |       |            |          |  
  27. |   2 |   LOAD AS SELECT           | SYS_TEMP_0FD9D6605_E16CE |       |       |            |          |  
  28. |*  3 |    TABLE ACCESS FULL       | EMP                      |     1 |    21 |     3   (0)| 00:00:01 |  
  29. |   4 |     SORT AGGREGATE         |                          |     1 |     4 |            |          |  
  30. |   5 |      TABLE ACCESS FULL     | EMP                      |    14 |    56 |     3   (0)| 00:00:01 |  
  31. |   6 |   VIEW                     |                          |     1 |    26 |     2   (0)| 00:00:01 |  
  32. |   7 |    TABLE ACCESS FULL       | SYS_TEMP_0FD9D6605_E16CE |     1 |    17 |     2   (0)| 00:00:01 |  
  33. -------------------------------------------------------------------------------------------------------  
  34.   
  35. Predicate Information (identified by operation id):  
  36. ---------------------------------------------------  
  37.   
  38.    3 - filter("SAL"> (SELECT AVG("SAL"FROM "EMP" "EMP"))  
  39.   
  40. 19 rows selected.  
  41.   
  42. 去掉 /*+ materialize */ ,由于只访问了一次a,所以CBO不会将a的查询结果生成一个临时表  
  43.   
  44. SQL> explain plan for  
  45. with a as (select ename,job,deptno from emp where sal>(select avg(sal) from emp))  
  46. select * from a ;  2    3  
  47.   
  48. Explained.  
  49.   
  50. SQL> select * from table(dbms_xplan.display);  
  51.   
  52. PLAN_TABLE_OUTPUT  
  53. ----------------------------------------------------------------------------  
  54. Plan hash value: 1876299339  
  55.   
  56. ----------------------------------------------------------------------------  
  57. | Id  | Operation           | Name | Rows  | Bytes | Cost (%CPU)| Time     |  
  58. ----------------------------------------------------------------------------  
  59. |   0 | SELECT STATEMENT    |      |     1 |    21 |     6   (0)| 00:00:01 |  
  60. |*  1 |  TABLE ACCESS FULL  | EMP  |     1 |    21 |     3   (0)| 00:00:01 |  
  61. |   2 |   SORT AGGREGATE    |      |     1 |     4 |            |          |  
  62. |   3 |    TABLE ACCESS FULL| EMP  |    14 |    56 |     3   (0)| 00:00:01 |  
  63. ----------------------------------------------------------------------------  
  64.   
  65. Predicate Information (identified by operation id):  
  66. ---------------------------------------------------  
  67.   
  68.    1 - filter("SAL"> (SELECT AVG("SAL"FROM "EMP" "EMP"))  
  69.   
  70. 15 rows selected.  
  71.   
  72.   
  73.   
  74. WITH AS 语句调用一次 使用多次 需要写hints  
  75.   
  76.   
  77. 如果  表 只 扫描 1次,你些materialize hints 结果读了一次 还写入temp, 再从temp读出来  
  78. 临时表写入是1次,但是读要多次。  
  79.   
  80.   
  81. 继续测试:  
  82. SQL> explain plan for  
  83. with a as (select ename,job,deptno from emp where sal>(select avg(sal) from emp))  
  84. select * from a union all select * from a;  2    3    
  85.   
  86. Explained.  
  87.   
  88. SQL> select * from table(dbms_xplan.display());  
  89.   
  90. PLAN_TABLE_OUTPUT  
  91. ------------------------------------------------------------------------------------------------------------------------------------------------------------  
  92.   
  93. --------------------------------------------  
  94. Plan hash value: 2575088720  
  95.   
  96. --------------------------------------------------------------------------------------------------------  
  97. | Id  | Operation          | Name              | Rows  | Bytes | Cost (%CPU)| Time     |  
  98. --------------------------------------------------------------------------------------------------------  
  99. |   0 | SELECT STATEMENT       |                   |     2 |    52 |     4  (50)| 00:00:01 |  
  100. |   1 |  TEMP TABLE TRANSFORMATION |                   |       |       |        |          |  
  101. |   2 |   LOAD AS SELECT       | SYS_TEMP_0FD9D6601_4DC46A |       |       |        |          |  
  102. |*  3 |    TABLE ACCESS FULL       | EMP               |     1 |    39 |     3   (0)| 00:00:01 |  
  103. |   4 |     SORT AGGREGATE     |                   |     1 |    13 |        |          |  
  104. |   5 |      TABLE ACCESS FULL     | EMP               |    14 |   182 |     3   (0)| 00:00:01 |  
  105. |   6 |   UNION-ALL        |                   |       |       |        |          |  
  106. |   7 |    VIEW            |                   |     1 |    26 |     2   (0)| 00:00:01 |  
  107. |   8 |     TABLE ACCESS FULL      | SYS_TEMP_0FD9D6601_4DC46A |     1 |    26 |     2   (0)| 00:00:01 |  
  108. |   9 |    VIEW            |                   |     1 |    26 |     2   (0)| 00:00:01 |  
  109. |  10 |     TABLE ACCESS FULL      | SYS_TEMP_0FD9D6601_4DC46A |     1 |    26 |     2   (0)| 00:00:01 |  
  110. --------------------------------------------------------------------------------------------------------  
  111.   
  112. Predicate Information (identified by operation id):  
  113. ---------------------------------------------------  
  114.   
  115.    3 - filter("SAL"> (SELECT AVG("SAL"FROM "EMP" "EMP"))  
  116.   
  117. Note  
  118. -----  
  119.    - dynamic sampling used for this statement (level=2)  
  120.   
  121. 26 rows selected.  
  122.   
  123. 充分证明 :  
  124. 1.当with as 语句没有被调用2次以上时,如果需要访问多次,那么需要加hints  /*+ materialize */   
  125.   
  126. 2.如果with as 语句被调用2次以上时,自动会将 with as 短语的数据放入一个临时表,这个时候不用写materialize hint  


0 0
原创粉丝点击