8:30         到公司
8:30    12:00   新闻
13:00   13:30   case
13:30           学习

总结一下oracle的hint

在调优中最常用的两种hint就是 access hint 和 join hint,先看一下access hint

  • FULL

  • CLUSTER

  • HASH

  • INDEX and NO_INDEX

  • INDEX_ASC and INDEX_DESC

  • INDEX_COMBINE and INDEX_JOIN

  • INDEX_JOIN

  • INDEX_FFS and NO_INDEX_FFS

  • INDEX_SS and NO_INDEX_SS

  • INDEX_SS_ASC and INDEX_SS_DESC

这些列出来的HINT中

FULL用于全表扫描

INDEX用于采用INDEX扫描

SQL> explain plan for select /*+ INDEX(objects SYS_C0087859)*/ object_id from kramer.objects;
SQL> select * from table(dbms_xplan.display);
-----------------------------------------------------------------------------
| Id  | Operation         | Name    | Rows  | Bytes | Cost (%CPU)| Time     |
-----------------------------------------------------------------------------
|   0 | SELECT STATEMENT  |         | 55265 |   701K|   182   (4)| 00:00:03 |
|   1 |  TABLE ACCESS FULL| OBJECTS | 55265 |   701K|   182   (4)| 00:00:03 |
-----------------------------------------------------------------------------

注意,上面的例子虽然使用了 hint 但是仍然采用了全表扫描,这是因为要使用的索引列中有NULL值。  NULL值在索引中不会存储,所以oracle认为索引扫描不能实现SQL语句的逻辑需求,所以忽略了这个hint。 下面我们把索引列设为NOT NULL,这样就可以成功使用索引

SQL> alter table kramer.objects modify object_id not null;
SQL> explain plan for select /*+ INDEX(objects SYS_C0087859)*/ object_id from kramer.objects;
---------------------------------------------------------------------------------
| Id  | Operation        | Name         | Rows  | Bytes | Cost (%CPU)| Time     |
---------------------------------------------------------------------------------
|   0 | SELECT STATEMENT |              | 55265 |   701K|   133   (4)| 00:00:02 |
|   1 |  INDEX FULL SCAN | SYS_C0087859 | 55265 |   701K|   133   (4)| 00:00:02 |
---------------------------------------------------------------------------------

下面是使用了这个hint后查询优化器的行为。

  • If the INDEX hint specifies a single available index, then the database performs a scan on this index. The optimizer does not consider a full table scan or a scan of another index on the table.

  • For a hint on a combination of multiple indexes, Oracle recommends using INDEX_COMBINE rather than INDEX, because it is a more versatile hint. If the INDEX hint specifies a list of available indexes, then the optimizer considers the cost of a scan on each index in the list and then performs the index scan with the lowest cost. The database can also choose to scan multiple indexes from this list and merge the results, if such an access path has the lowest cost. The database does not consider a full table scan or a scan on an index not listed in the hint.

    如果在hint中列出了多个索引,最好使用INDEX_COMBINE 这个hint。 如果使用的是hint 加多个索引的列表,查询优化器会根据自己的计算的最低开销选取其中一个或者若干个index来访问,但不会考虑全表扫描或者没有在列表中提到的index。

  • If the INDEX hint specifies no indexes, then the optimizer considers the cost of a scan on each available index on the table and then performs the index scan with the lowest cost. The database can also choose to scan multiple indexes and merge the results, if such an access path has the lowest cost. The optimizer does not consider a full table scan.

    在没指定index的情况下,就相当于在列表里提到了要访问表的所有index。

NO_INDEX用于不采用指定index扫描

SQL> explain plan for select /*+ no_index(objects) */ object_id from kramer.objects where object_id=222;SQL> select * from table(dbms_xplan.display);-----------------------------------------------------------------------------
| Id  | Operation         | Name    | Rows  | Bytes | Cost (%CPU)| Time     |
-----------------------------------------------------------------------------
|   0 | SELECT STATEMENT  |         |   652 |  8476 |   184   (5)| 00:00:03 |
|*  1 |  TABLE ACCESS FULL| OBJECTS |   652 |  8476 |   184   (5)| 00:00:03 |
-----------------------------------------------------------------------------

下面是采取了这个hint后查询优化器的思路

  • If this hint specifies a single available index, then the optimizer does not consider a scan on this index. Other indexes not specified are still considered.

  • If this hint specifies a list of available indexes, then the optimizer does not consider a scan on any of the specified indexes. Other indexes not specified in the list are still considered.

  • If this hint specifies no indexes, then the optimizer does not consider a scan on any index on the table. This behavior is the same as a NO_INDEX hint that specifies a list of all available indexes for the table.

INDEX_ASC INDEX_DESC

用于采取 升序 扫描索引,例如下面的例子

SQL> explain plan for select /*+ index_asc(objects SYS_C0087859)*/ object_id from kramer.objects order by object_id desc;Explained.SQL> select * from table(dbms_xplan.display);PLAN_TABLE_OUTPUT
----------------------------------------------------------------------------------------------------
Plan hash value: 3091698887-----------------------------------------------------------------------------------------
| Id  | Operation        | Name         | Rows  | Bytes |TempSpc| Cost (%CPU)| Time     |
-----------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT |              | 55265 |   701K|       |   413   (5)| 00:00:05 |
|   1 |  SORT ORDER BY   |              | 55265 |   701K|  2184K|   413   (5)| 00:00:05 |
|   2 |   INDEX FULL SCAN| SYS_C0087859 | 55265 |   701K|       |   133   (4)| 00:00:02 |
-----------------------------------------------------------------------------------------

本来在语句中指定了 order by objecrt_id desc , 为了避免排序操作,oracle会采取降序扫描索引的方式来访问表,但是我们指定了hint,所以采取的是升序。 index_desc的例子跟这个一样。

INDEX_COMBINE

这个HINT花了我好长时间,看它的官方说明如下:

The INDEX_COMBINE hint instructs the optimizer to use a bitmap access path for the table. If indexspec is omitted from the INDEX_COMBINE hint, then the optimizer uses whatever Boolean combination of indexes has the best cost estimate for the table. If you specify indexspec, then the optimizer tries to use some Boolean combination of the specified indexes. Each parameter serves the same purpose as in "INDEX Hint". For example:

它是说,如果指定了这个hint,oracle可能会把一些索引转化成位图索引,然后把这些位图索引进行位操作,以缩小结果集。也就是说有时候你建立的索引是B-Tree索引,但是oracle仍然会把他们转化成位图索引然后来操作,为了理解这一过程,专门去查了位图索引的工作方式以及这样转化的意义。下面总结一下:

位图索引工作方式:参见concept bitmap index

B-Tree转化成位图索引的意义:位图索引在进行count,and,or等操作时效率较高,所以有时查询优化器会把B-tree扫描到的rowid 转化成一个位图索引,然后对其进行count,and,or等操作。

下面看使用这个hint的例子:

http://www.itpub.net/thread-1601847-1-1.html

INDEX_JOINE

这个hint的目的是让oracle不必返回表中取数据,如果index中有的话。例如:

SQL>  create table test as select object_id,object_type,status from dba_objects;Table created.SQL> create index tobject_id on test(object_id);Index created.SQL>  create index tobject_type on test(object_type);Index created.SQL> explain plan for   select  object_id,object_type from test where object_id=15847 and object_type='JAVA CLASS';------------------------------------------------------------------------------------------
| Id  | Operation                   | Name       | Rows  | Bytes | Cost (%CPU)| Time     |
------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT            |            |     3 |    72 |     2   (0)| 00:00:01 |
|*  1 |  TABLE ACCESS BY INDEX ROWID| TEST       |     3 |    72 |     2   (0)| 00:00:01 |
|*  2 |   INDEX RANGE SCAN          | TOBJECT_ID |     3 |       |     1   (0)| 00:00:01 |
------------------------------------------------------------------------------------------

上面没有使用hint,所以oracle的做法是在tobject_id这个索引中获得rowid然后根据rowid去表中提取数据。但是如果我们使用了index_joine,那么oracle会访问tobject_id和tobject_type这两个索引,然后把获取的数据连接返回,这样就不用返回表取数据了。

SQL> explain plan for select /*+ index_join(test tobject_id tobject_type) */  object_id,object_type from test where object_id=15847 and object_type='JAVA CLASS';--------------------------------------------------------------------------------------------------
| Id  | Operation                     | Name             | Rows  | Bytes | Cost (%CPU)| Time     |
--------------------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT              |                  |     3 |    72 |     4  (25)| 00:00:01 |
|*  1 |  VIEW                         | index$_join$_001 |     3 |    72 |     4  (25)| 00:00:01 |
|*  2 |   HASH JOIN                   |                  |       |       |            |          |
|*  3 |    INDEX RANGE SCAN           | TOBJECT_ID       |     3 |    72 |     1   (0)| 00:00:01 |
|   4 |    BITMAP CONVERSION TO ROWIDS|                  |     3 |    72 |     2   (0)| 00:00:01 |
|*  5 |     BITMAP INDEX SINGLE VALUE | TOBJECT_TYPE     |       |       |            |          |

INDEX_FFS

该hint指定采用 index fast full scan

SQL> explain plan for select /*+ INDEX_FFS(TEST TOBJECT_ID) */  object_id from test;Explained.SQL> select * from table(dbms_xplan.display);PLAN_TABLE_OUTPUT
------------------------------------------------------------------------------------------------------------------------------------------------------
Plan hash value: 2112390145-----------------------------------------------------------------------------------
| Id  | Operation            | Name       | Rows  | Bytes | Cost (%CPU)| Time     |
-----------------------------------------------------------------------------------
|   0 | SELECT STATEMENT     |            | 56227 |   274K|    32  (10)| 00:00:01 |
|   1 |  INDEX FAST FULL SCAN| TOBJECT_ID | 56227 |   274K|    32  (10)| 00:00:01 |
-----------------------------------------------------------------------------------8 rows selected.

关于这个hint要注意的一点是,和index hint一样,如果object_id 包含null,那么这个hint就有可能不被使用, 因为在一列的hint上不会存储null。

INDEX_SS

An index skip scan uses logical subindexes of a composite index. The database "skips" through a single index as if it were searching separate indexes. Skip scanning is beneficial if there are few distinct values in the leading column of a composite index and many distinct values in the nonleading key of the index.

The database may choose an index skip scan when the leading column of the composite index is not specified in a query predicate. For example, assume that you run the following query for a customer in the sh.customers table:

SELECT * FROM sh.customers WHERE cust_email = 'Abbey@company.com';

The customers table has a column cust_gender whose values are either M or F. Assume that a composite index exists on the columns (cust_gendercust_email). Example 3-1 shows a portion of the index entries.

Example 3-1 Composite Index Entries

F,Wolf@company.com,rowid F,Wolsey@company.com,rowid F,Wood@company.com,rowid F,Woodman@company.com,rowid F,Yang@company.com,rowid F,Zimmerman@company.com,rowid M,Abbassi@company.com,rowid M,Abbey@company.com,rowid 

The database can use a skip scan of this index even though cust_gender is not specified in the WHERE clause.

In a skip scan, the number of logical subindexes is determined by the number of distinct values in the leading column. InExample 3-1, the leading column has two possible values. The database logically splits the index into one subindex with the key F and a second subindex with the key M.

When searching for the record for the customer whose email is Abbey@company.com, the database searches the subindex with the value F first and then searches the subindex with the value M. Conceptually, the database processes the query as follows:

SELECT * FROM sh.customers WHERE cust_gender = 'F'    AND cust_email = 'Abbey@company.com' UNION ALL SELECT * FROM sh.customers WHERE cust_gender = 'M'   AND cust_email = 'Abbey@company.com';结论:
1、ORACLE太智能了吧。。。这都能分析。。。
2、如果WHERE语句的过滤列,没有单独的索引,也并不表示数据库就一定不会使用索引扫描。疑问:
什么情况下会自动使用这种索引扫描呢?就是说,主索引列的可能的取值情况,少到什么程度,
数据库才会采用这种“索引跳跃扫描”呢?

2012年4月10日 周二相关推荐

  1. 好几天忘记笑了~2012年9月10日

    1.老师领着学生到鱼塘体验摸鱼,一时兴起问道:"小伙子们,谁知道浑水摸鱼什么意思?" 颜起:"浑了的水就能摸到鱼." 颜明:"起,别那么俗好不,肯定有 ...

  2. DS, DB, WEB模块的安装(环境搭建) 学习日志 2012年7月10日

    一.关于统筹模块的安装步骤: 1.将安装包以smsds用户二进制方式上传至"/home/smsds"目录. 2.以smsds用户登录系统. 3.删除"/home/smsd ...

  3. 2012年6月10日免费http代理大全

    111.249.150.2:8088@HTTP;台湾省 119.146.223.100:80@HTTP;广东省珠海市 电信 119.146.223.41:80@HTTP;广东省珠海市 电信 119.1 ...

  4. 2012年12月10日

    一.正则表达式教程 有一个经典的教程: 正则表达式30分钟入门教 程,大家可以搜索一下.我忘了在哪地址! 这个教程的确很简单,看完基本上写一些简单的正则就没有问题了.正则是一个需要长期使用的工具,隔段 ...

  5. 如何解决2012年7月1日增加闰秒后引起linux系统重启问题

    国际地球自转和参考坐标系统服务(IERS)将在格林威治时间2012年6月30日午夜增加一闰秒(维基百科关于闰秒的说明),由于Linux kernel和Posix关于NTP时间跳变的标准不同,将在201 ...

  6. 从腾讯朋友圈揭秘内部AI部门竞争关系,谁能像微信当年一样熬出头? By 微胖2017年11月10日 09:06 撰文 | 宇多田 在腾讯合作伙伴大会上,腾讯首席运营官任宇昕提出的「AI in All」

    从腾讯朋友圈揭秘内部AI部门竞争关系,谁能像微信当年一样熬出头? By 微胖2017年11月10日 09:06 撰文 | 宇多田 在腾讯合作伙伴大会上,腾讯首席运营官任宇昕提出的「AI in All」 ...

  7. 2012年11月04日春色满园关不住freeeim源码哇

    摘要:2012年11月04日春色满园关不住freeeim源码哇,贴纸出来了,一天早晨我去上学,您回去吧,突然一条狗向我跑来,表姐又买了贴纸本,它以飞一般的速度窜到天空,我跑回去就行了,看见老师还在为我 ...

  8. 12月10日站立会议

    12月10日(周一)完成情况: 今天已经接近第二个冲刺周期的尾声了,今天我们在单词测试的基础上加入了单词测试后的正误判断,该功能适应了用户的需求,使用户可以在测试之后看到自己的测试结果,从而来判断自己 ...

  9. 12月10日周日下午广州Linuxer聚会(4大演讲主题+蜗窝大侠郭健主持)

    12月10日周日下午广州Linuxer聚会,四大主题演讲,加蜗窝大侠郭健主持.活动自发组织,就Linux论道,人人畅所欲言.欢迎报名. 相关活动: 已成最美好的回忆:北京Linuxer第一次线下交流研 ...

最新文章

  1. AI助力清华博士进入周杰伦战队,预告AI应用迎来黄金时代?
  2. Windows 7 开发系列汇总
  3. jquery json
  4. HDU-4568 Hunter 状态压缩
  5. pycharm控制台调试程序
  6. day24 面向对象与实例属性
  7. 【Linux】一步一步学Linux——stat命令(77)
  8. Java线程安全以及线程安全的实现方式和内存模型(JMM)
  9. VS2010,C++ 制作静态库(*.lib),并使用
  10. linux shell: 搜索字符串,剔除包含特定字符的行
  11. C++类的继承与派生
  12. asp 文件上传 代码
  13. 干货!Python与MySQL数据库的交互实战
  14. 洛谷 P1032 字串变换
  15. MSN Messenger
  16. Python 爬取朋友圈最新方法!!(文末赠书)
  17. 2021年起重机械指挥复审模拟考试及起重机械指挥考试试题
  18. 计算机研究生考试题,全国研究生考试计算机统考试题及答案-20210522014129.docx-原创力文档...
  19. 深入理解BFC与IFC
  20. 分享电脑便捷妙招,电脑小白们快码住

热门文章

  1. Nginx四层代理和7层反向代理
  2. 车库咖啡参与投资拍摄的电影《当我们海阔天空》即将上映
  3. oracle 日期 加一年,JS 取加一年减一天的时间
  4. UE4 安卓触摸事件相关问题
  5. 一般集合的合并(并集)
  6. R语言无法从GitLAB/GITHUB远程安装
  7. 那些辞职创业的互联网人现在怎么样了?
  8. XP 小技巧( 隐藏文件、mp3转换WMA )
  9. 计算机基础知识回答提,计算机基础知识问答
  10. 在歌星大奖赛中,有10个评委为参赛的选手打分,分数为1~100分。选手最后得分为:去掉一个最高分和一个最低分后其余8个分数的平均值。同时对评委评分进行裁判,即在10个评委中找出最公平(即评分最接返平均