对于hints index() 的学习 (一)

对于hints index() 的学习 (一)

一、如何使用 /*+ index()*/   

The format for an index hint is:

 select /*+ index(TABLE_NAME INDEX_NAME) */ col1...

There are a number of rules that need to be applied to this hint:

1 The TABLE_NAME is mandatory in the hint
2 The table alias MUST be used if the table is aliased in the query
3 If TABLE_NAME or alias is spelled incorrectly then the hint will not be used.
4 The INDEX_NAME is optional. 
5 If an INDEX_NAME is entered without a TABLE_NAME then the hint will not be 
  applied.
6 If a TABLE_NAME is supplied on its own then the optimizer will decide 
  which index to use based on statistics.
7 If the INDEX_NAME is spelt incorrectly but the TABLE_NAME is spelled correctly 
  then the hint will not be applied even though the TABLE_NAME is correct.
8 If there are multiple index hints to be applied, then the simplest way of
  addressing this is to repeat the index hint syntax for each index e.g.:

     select /*+ index(TABLE_NAME1 INDEX_NAME1) index(TABLE_NAME2 INDEX_NAME2) */ col1...

9 Remember that the parser/optimizer may have transformed/rewritten the query
  or may have chosen an access path which make the use of the index invalid and
  this may result in the index not being used.

NB Please note that as long as the index() hint structure is correct
   it will force the use of the Cost Based Optimizer (CBO). This will happen
   even if the alias or table name is incorrect.

二、测试


 INDEX_NAME                     COLUMN_NAME
------------------------------ ----------------
IND_T1                             ENAME
II                                          EMPNO

SQL> select /*+index(t1) */empno from t1;

已选择12行。
执行计划
----------------------------------------------------------
Plan hash value: 3617692013
--------------------------------------------------------------------------
| Id  | Operation         | Name | Rows  | Bytes | Cost (%CPU)| Time     |
--------------------------------------------------------------------------
|   0 | SELECT STATEMENT  |      |    12 |    48 |     3   (0)| 00:00:01 |
|   1 |  TABLE ACCESS FULL| T1   |    12 |    48 |     3   (0)| 00:00:01 |
--------------------------------------------------------------------------

通过测试发现,此hints 没有起作用,但是也没有什么地方写错,最后加了一个主键后,走hints

SQL> select /*+ index(t1)*/t1.ename from T1;
已选择12行。
执行计划
----------------------------------------------------------
Plan hash value: 1552010074
------------------------------------------------------------------------------------
| Id  | Operation                   | Name | Rows  | Bytes | Cost (%CPU)| Time     |
------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT            |      |    12 |    72 |     2   (0)| 00:00:01 |
|   1 |  TABLE ACCESS BY INDEX ROWID| T1   |    12 |    72 |     2   (0)| 00:00:01 |
|   2 |   INDEX FULL SCAN           | II   |    12 |       |     1   (0)| 00:00:01 |
------------------------------------------------------------------------------------


下面我们逐一测试:

  1. 1、 index() 里的table_name 是强制性的提示,index_name是可选性的,如果 table_name 有别名,那么hints 中的表名也必须用别名  
  2. SQL> select /*+ index(t1)*/ ename from T1 a;  
  3.   
  4. 已选择12行。  
  5.   
  6.   
  7. 执行计划  
  8. ----------------------------------------------------------  
  9. Plan hash value: 3617692013  
  10.   
  11. --------------------------------------------------------------------------  
  12. | Id  | Operation         | Name | Rows  | Bytes | Cost (%CPU)| Time     |  
  13. --------------------------------------------------------------------------  
  14. |   0 | SELECT STATEMENT  |      |    12 |    72 |     3   (0)| 00:00:01 |  
  15. |   1 |  TABLE ACCESS FULL| T1   |    12 |    72 |     3   (0)| 00:00:01 |  
  16. --------------------------------------------------------------------------  
  17.   
  18. 2、hints中 index()里的table_name 是必须的,但是index_name不是必须的,也就是说hints中只写index_name不写table_name,那么hints不会被使用  
  19. SQL> select /*+ index(ind_t1)*/ ename from T1 a;  
  20. 已选择12行。  
  21. 执行计划  
  22. ----------------------------------------------------------  
  23. Plan hash value: 3617692013  
  24.   
  25. --------------------------------------------------------------------------  
  26. | Id  | Operation         | Name | Rows  | Bytes | Cost (%CPU)| Time     |  
  27. --------------------------------------------------------------------------  
  28. |   0 | SELECT STATEMENT  |      |    12 |    72 |     3   (0)| 00:00:01 |  
  29. |   1 |  TABLE ACCESS FULL| T1   |    12 |    72 |     3   (0)| 00:00:01 |  
  30. --------------------------------------------------------------------------  
  31. 3、如果hints中的table_name或者别名写的不正确,那么hints就不会被使用  
  32. SQL> select /*+ index(aa)*/ ename from T1 a;  
  33. 已选择12行。  
  34. 执行计划  
  35. ----------------------------------------------------------  
  36. Plan hash value: 3617692013  
  37.   
  38. --------------------------------------------------------------------------  
  39. | Id  | Operation         | Name | Rows  | Bytes | Cost (%CPU)| Time     |  
  40. --------------------------------------------------------------------------  
  41. |   0 | SELECT STATEMENT  |      |    12 |    72 |     3   (0)| 00:00:01 |  
  42. |   1 |  TABLE ACCESS FULL| T1   |    12 |    72 |     3   (0)| 00:00:01 |  
  43. --------------------------------------------------------------------------  
  44.   
  45. SQL> select /*+ index(a ii_t1)*/ ename from T1 a;  
  46.   
  47. 已选择12行。  
  48.   
  49.   
  50. 执行计划  
  51. ----------------------------------------------------------  
  52. Plan hash value: 3617692013  
  53.   
  54. --------------------------------------------------------------------------  
  55. | Id  | Operation         | Name | Rows  | Bytes | Cost (%CPU)| Time     |  
  56. --------------------------------------------------------------------------  
  57. |   0 | SELECT STATEMENT  |      |    12 |    72 |     3   (0)| 00:00:01 |  
  58. |   1 |  TABLE ACCESS FULL| T1   |    12 |    72 |     3   (0)| 00:00:01 |  
  59. --------------------------------------------------------------------------  
  60.   
  61.   
  62. 4、如果hints中写了table_name不写索引名,那么优化器会根据统计信息选择索引  
  63. QL> select /*+ index(a)*/ ename from T1 a;  
  64. 已选择12行。  
  65.   
  66. 执行计划  
  67. ---------------------------------------------------------  
  68. lan hash value: 1552010074  
  69.   
  70. -----------------------------------------------------------------------------------  
  71.  Id  | Operation                   | Name | Rows  | Bytes | Cost (%CPU)| Time     |  
  72. -----------------------------------------------------------------------------------  
  73.    0 | SELECT STATEMENT            |      |    12 |    72 |     2   (0)| 00:00:01 |  
  74.    1 |  TABLE ACCESS BY INDEX ROWID| T1   |    12 |    72 |     2   (0)| 00:00:01 |  
  75.    2 |   INDEX FULL SCAN           | II   |    12 |       |     1   (0)| 00:00:01 |  
  76. -----------------------------------------------------------------------------------  
  77.   
  78. 5、如果hints中的table_name 写错,而索引写正确 ,那么hints就不会被使用  
  79. SQL> select /*+ index(aa ii )*/ ename from T1 a;  
  80. 已选择12行。  
  81. 执行计划  
  82. ----------------------------------------------------------  
  83. Plan hash value: 3617692013  
  84.   
  85. --------------------------------------------------------------------------  
  86. | Id  | Operation         | Name | Rows  | Bytes | Cost (%CPU)| Time     |  
  87. --------------------------------------------------------------------------  
  88. |   0 | SELECT STATEMENT  |      |    12 |    72 |     3   (0)| 00:00:01 |  
  89. |   1 |  TABLE ACCESS FULL| T1   |    12 |    72 |     3   (0)| 00:00:01 |  
  90. --------------------------------------------------------------------------  
  91.   
  92. 7、如果有多个索引要使用那么可以使用  /*+ index(TABLE_NAME1 INDEX_NAME1) index(TABLE_NAME2 INDEX_NAME2) */
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值