专栏首页bisal的个人杂货铺[Oracle]-[索引][HINT][执行计划]-带HINT的索引执行计划

[Oracle]-[索引][HINT][执行计划]-带HINT的索引执行计划

谭老师的《Oracle 10g 性能分析与优化思路》第六章hint部分介绍: 举例: create table t(id int); create index t_idx on t(id);

SQL> select /*+ index(t t_idx) */ count(*) from t;

Execution Plan

----------------------------------------------------------

Plan hash value: 4075463224

-------------------------------------------------------------------

| Id  | Operation          | Name | Rows  | Cost (%CPU)| Time     |

-------------------------------------------------------------------

|   0 | SELECT STATEMENT   |      |     1 |     2   (0)| 00:00:01 |

|   1 |  SORT AGGREGATE    |      |     1 |            |          |

|   2 |   TABLE ACCESS FULL| T  |     3 |     2   (0)| 00:00:01 |

-------------------------------------------------------------------

Note

-----

   - dynamic sampling used for this statement

这里忽略了HINT,解释是:因为我们要对表的记录求总数,我们创建的索引并没有指定索引字段T不能为空,所以如果CBO选择在索引上做COUNT,当索引字段上有空值时,COUNT的结果必然不准确。

SQL> select /*+ index(t, t_idx) */ count(id) from t;

Execution Plan

----------------------------------------------------------

Plan hash value: 4235589928

----------------------------------------------------------------------------

| Id  | Operation        | Name    | Rows  | Bytes | Cost (%CPU)| Time     |

----------------------------------------------------------------------------

|   0 | SELECT STATEMENT |         |     1 |    13 |     1   (0)| 00:00:01 |

|   1 |  SORT AGGREGATE  |         |     1 |    13 |            |          |

|   2 |   INDEX FULL SCAN| T_IDX |     3 |    39 |     1   (0)| 00:00:01 |

----------------------------------------------------------------------------

Note

-----

   - dynamic sampling used for this statement

这里用到了HINT,解释是:因为我们只是对X字段做COUNT,id字段是索引字段,这个动作相当于COUNT索引上的所有id的键值,这个结果和对表上id字段做COUNT是一样的。

这点我觉得不是很准确。

如果是唯一性索引,则count(*)==count(索引字段)。

如果不是非唯一索引,则列中NULL值不会存入索引,因此count(*)>=count(索引字段)。

再做个实验:

CREATE TABLE TBL_SMALL (ID   NUMBER, NAME VARCHAR2(5) ); SQL> create index t_s_idx on tbl_small(id); create table tbl_big as select rownum id, object_name name from dba_objects where rownum<1000; SQL> create index t_b_idx on tbl_big(id); insert into tbl_big values('', ''); >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> SQL> select * from tbl_small;         ID NAME ---------- -----          2 b          1 a SQL> select count(*) from tbl_small;   COUNT(*) ----------          3 SQL> select count(id) from tbl_small; COUNT(ID) ----------          2 SQL> select count(*) from tbl_big;   COUNT(*) ----------       1000 SQL> select count(id) from tbl_big; COUNT(ID) ----------        999 SQL> set autot trace exp >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> TBL_SMALL表: SQL> select count(*) from tbl_small; Execution Plan ---------------------------------------------------------- Plan hash value: 1452584873 ------------------------------------------------------------------------ | Id  | Operation          | Name      | Rows  | Cost (%CPU)| Time     | ------------------------------------------------------------------------ |   0 | SELECT STATEMENT   |           |     1 |     2   (0)| 00:00:01 | |   1 |  SORT AGGREGATE    |           |     1 |            |          | |   2 |   TABLE ACCESS FULL| TBL_SMALL |     3 |     2   (0)| 00:00:01 | ------------------------------------------------------------------------ Note -----    - dynamic sampling used for this statement SQL> select count(id) from tbl_small; Execution Plan ---------------------------------------------------------- Plan hash value: 1539159417 ---------------------------------------------------------------------------- | Id  | Operation        | Name    | Rows  | Bytes | Cost (%CPU)| Time     | ---------------------------------------------------------------------------- |   0 | SELECT STATEMENT |         |     1 |    13 |     1   (0)| 00:00:01 | |   1 |  SORT AGGREGATE  |         |     1 |    13 |            |          | |   2 |   INDEX FULL SCAN| T_S_IDX |     3 |    39 |     1   (0)| 00:00:01 | ---------------------------------------------------------------------------- Note -----    - dynamic sampling used for this statement SQL> select /*+ index(tbl_small, t_s_idx) */ count(*) from tbl_small; Execution Plan ---------------------------------------------------------- Plan hash value: 1452584873 ------------------------------------------------------------------------ | Id  | Operation          | Name      | Rows  | Cost (%CPU)| Time     | ------------------------------------------------------------------------ |   0 | SELECT STATEMENT   |           |     1 |     2   (0)| 00:00:01 | |   1 |  SORT AGGREGATE    |           |     1 |            |          | |   2 |   TABLE ACCESS FULL| TBL_SMALL |     3 |     2   (0)| 00:00:01 | ------------------------------------------------------------------------ Note -----    - dynamic sampling used for this statement SQL> select /*+ index(tbl_small, t_s_idx) */ count(id) from tbl_small; Execution Plan ---------------------------------------------------------- Plan hash value: 1539159417 ---------------------------------------------------------------------------- | Id  | Operation        | Name    | Rows  | Bytes | Cost (%CPU)| Time     | ---------------------------------------------------------------------------- |   0 | SELECT STATEMENT |         |     1 |    13 |     1   (0)| 00:00:01 | |   1 |  SORT AGGREGATE  |         |     1 |    13 |            |          | |   2 |   INDEX FULL SCAN| T_S_IDX |     3 |    39 |     1   (0)| 00:00:01 | ---------------------------------------------------------------------------- Note -----    - dynamic sampling used for this statement >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> TBL_BIG表: SQL> select count(*) from tbl_big; Execution Plan ---------------------------------------------------------- Plan hash value: 475686685 ---------------------------------------------------------------------- | Id  | Operation          | Name    | Rows  | Cost (%CPU)| Time     | ---------------------------------------------------------------------- |   0 | SELECT STATEMENT   |         |     1 |     3   (0)| 00:00:01 | |   1 |  SORT AGGREGATE    |         |     1 |            |          | |   2 |   TABLE ACCESS FULL| TBL_BIG |  1000 |     3   (0)| 00:00:01 | ---------------------------------------------------------------------- Note -----    - dynamic sampling used for this statement SQL> select count(id) from tbl_big; Execution Plan ---------------------------------------------------------- Plan hash value: 2252048431 -------------------------------------------------------------------------------- | Id  | Operation             | Name    | Rows  | Bytes | Cost (%CPU)| Time -------------------------------------------------------------------------------- |   0 | SELECT STATEMENT      |         |     1 |    13 |     3   (0)| 00:00:01 |   1 |  SORT AGGREGATE       |         |     1 |    13 |            | |   2 |   INDEX FAST FULL SCAN| T_B_IDX |  1000 | 13000 |     3   (0)| 00:00:01 | -------------------------------------------------------------------------------- Note -----    - dynamic sampling used for this statement SQL> select /*+ index(tbl_big, t_b_idx) */ count(*) from tbl_big; Execution Plan ---------------------------------------------------------- Plan hash value: 475686685 ---------------------------------------------------------------------- | Id  | Operation          | Name    | Rows  | Cost (%CPU)| Time     | ---------------------------------------------------------------------- |   0 | SELECT STATEMENT   |         |     1 |     3   (0)| 00:00:01 | |   1 |  SORT AGGREGATE    |         |     1 |            |          | |   2 |   TABLE ACCESS FULL| TBL_BIG |  1000 |     3   (0)| 00:00:01 | ---------------------------------------------------------------------- Note -----    - dynamic sampling used for this statement SQL> select /*+ index(tbl_big, t_b_idx) */ count(id) from tbl_big; Execution Plan ---------------------------------------------------------- Plan hash value: 1004523789 ---------------------------------------------------------------------------- | Id  | Operation        | Name    | Rows  | Bytes | Cost (%CPU)| Time     | ---------------------------------------------------------------------------- |   0 | SELECT STATEMENT |         |     1 |    13 |     5   (0)| 00:00:01 | |   1 |  SORT AGGREGATE  |         |     1 |    13 |            |          | |   2 |   INDEX FULL SCAN| T_B_IDX |  1000 | 13000 |     5   (0)| 00:00:01 | ---------------------------------------------------------------------------- Note -----    - dynamic sampling used for this statement 不同的点: 小表对id字段count,无论是否使用hint,都是INDEX FULL SCAN。 大表对id字段count,不带hint,是INDEX FAST FULL SCAN,对id字段count带hint,是INDEX FULL SCAN。(这里我感觉不带hint,CBO还能选择FFS的方式可能更优,但如果带了hint,则强制使用并不最优的FS)。

也可以参考我的帖子上其它的回复:

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

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • Linux下的yum怎么升级?

    Linux下我们安装软件,可能会需要安装各种包来支持,你可以从安装介质中找到rpm,手动安装,但最常用的,可能还是yum,省了很多烦恼。

    bisal
  • 一道SQL考题的更多思考

    问题1,方案1执行update,select的结果应该是(1e,2b),存在不匹配的记录,不会进行更新,是我贴错了,我的锅,

    bisal
  • 一个DATE数据类型的检索

    今天快下班时,兄弟团队过来问了个问题,一张表中的DATE类型字段在PLSQL-Developer中检索的时候,出现这种现象,如下所示,有记录存储的是"2019-...

    bisal
  • 通过执行计划中的CONCATENATION分析sql问题(r4笔记第16天)

    昨天开发的一个同事找到我,说写了一条sql语句,但是执行了半个小时还没有执行完,想让我帮忙看看是怎么回事。 他大体上给我讲了下逻辑,表bl1_rc_rates是...

    jeanron100
  • 如何利用Nexus 5伪造一张门禁卡

    文中提及的部分技术可能带有一定攻击性,仅供安全学习和教学用途,禁止非法使用! 0×00 前言 我租住的杭州一个老小区一年前出现了所谓的“出租房杀人事件”,事件过...

    FB客服
  • Pandas时序数据处理入门

    作为一个几乎每天处理时间序列数据的人,我发现pandas Python包对于时间序列的操作和分析非常有用。

    AiTechYun
  • 不可不知的基因组版本对应关系

    不同版本对应关系 hg19,GRCH37和Ensembl75是三种国际生物信息学数据库资源收集存储单位,即NCBI,UCSC和ENSEMBL各自发布的基因组信息...

    生信技能树
  • [ Shell篇 ] - AWK征服数据处理

    实际过程中一些从软件导出来的配置文件格式格式比较混乱,一般需要整理成特定的格式,才好处理,场景如下:

    程序手艺人
  • 生产环境sql语句调优实战第十篇(r3笔记第39天)

    陆陆续续写了九篇关于生产环境sql语句的调优案例,发现了不少问题,可能有些问题回头来看是比较低级的错误,稍加改动就能够运行在秒级,有些可能是在秒级到毫秒级的小步...

    jeanron100
  • Ctftool:一款功能强大的交互式CTF漏洞利用工具

    除此之外,Ctftool还允许研究人员根据自己的需要来编写一些简单的脚本来实现与CTF客户端或服务器端的自动化交互,以及执行简单的模糊测试任务。

    FB客服

扫码关注云+社区

领取腾讯云代金券