查看: 5428|回复: 19

查询条件包含组合索引所有键为啥执行计划走的是index skip scan???

[复制链接]
论坛徽章:
1
ITPUB十周年纪念徽章
日期:2011-11-01 16:23:26
跳转到指定楼层
1#
发表于 2011-10-9 22:48 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
本帖最后由 feiweiwei1985 于 2011-10-10 22:15 编辑

最近在生产环境发现一支交易的执行计划走的是index skip scan,语句为 select * from inct where master_ac_no='123456789012' and trn_date>=to_date('20110801','yyyymmdd') and trn_date<=to_date('20111001','yyyymmdd'); 其中inct表为交易表,数据量为30亿多,一级分区为trn_date(交易时间)的按月range分区,二级分区为master_ac_no(账号)的hash分区,索引为local index索引键为trn_date、master_ac_no组合索引。这里对于这样的语句where条件里有组合索引的所有键值,执行计划应该是index range scan 但是为什么走的却是index skip scan,查看了执行计划逻辑读比较高,求高手解答,问题困惑了几天了找不到原因。。。
论坛徽章:
42
ITPUB季度 技术新星
日期:2012-05-22 15:10:11祖母绿
日期:2013-09-13 21:16:10蓝锆石
日期:2013-09-13 21:15:34海蓝宝石
日期:2013-09-13 21:13:45最佳人气徽章
日期:2012-03-13 17:39:18优秀写手
日期:2013-12-18 09:29:11ITPUB社区12周年站庆徽章
日期:2013-10-17 13:56:592013年新春福章
日期:2013-02-25 14:51:24玉石琵琶
日期:2012-02-21 15:04:38ITPUB 11周年纪念徽章
日期:2012-10-09 18:08:15
2#
发表于 2011-10-9 23:00 | 只看该作者
跨分区导致?
明天去公司测试下

使用道具 举报

回复
论坛徽章:
1
ITPUB十周年纪念徽章
日期:2011-11-01 16:23:26
3#
 楼主| 发表于 2011-10-9 23:03 | 只看该作者
有别的类似的交易表就没有这样的情况,走的都是index range scan,试过了没跨月分区也会走index skip scan,很诡异

使用道具 举报

回复
论坛徽章:
1
ITPUB十周年纪念徽章
日期:2011-11-01 16:23:26
4#
 楼主| 发表于 2011-10-9 23:07 | 只看该作者
这个应该不是跨分区导致的,这种分区方式的应用在银行或者证券系统应该是挺常见的

使用道具 举报

回复
论坛徽章:
4
2011新春纪念徽章
日期:2011-02-18 11:42:49ITPUB十周年纪念徽章
日期:2011-11-01 16:26:292014年新春福章
日期:2014-02-18 16:44:08马上有对象
日期:2014-02-18 16:44:08
5#
发表于 2011-10-9 23:43 | 只看该作者
ORACLE官方说,在前导列唯一值较少的情况下,才会用到index skip can。
master_ac_no='123456789012' 这个是不是组合索引的前导列?逻辑值比较高,看看你的索引深度或rebuilt一下索引试试。

使用道具 举报

回复
求职 : 数据库管理员
论坛徽章:
18
迷宫蛋
日期:2011-06-01 15:32:28蛋疼蛋
日期:2011-10-27 13:21:25ITPUB十周年纪念徽章
日期:2011-11-01 16:19:41ITPUB社区千里马徽章
日期:2013-06-09 10:15:342014年新春福章
日期:2014-02-18 16:41:11马上有车
日期:2014-02-18 16:41:11沸羊羊
日期:2015-03-04 14:43:432015年新春福章
日期:2015-03-06 11:57:31
6#
发表于 2011-10-10 08:25 | 只看该作者
本帖最后由 nmgzw 于 2011-10-10 08:26 编辑
  1. 请参考!这个没有什么原因能解释,只能说是oracle一个bug!
  2. 参照CBO一书原文如下!

  3. create index t1_i1 on t1(n1, ind_pad, n2)

  4. More on Range-based Tests
  5. We took the easy option, and did a range-based test on the last column in the index. What
  6. happens if we do a range-based test on an earlier column in the index? Try this, for example:
  7. alter session set "_optimizer_skip_scan_enabled"=false;
  8. select
  9. /*+ index(t1) */
  10. small_vc
  11. from
  12. t1
  13. where
  14. n1 between 1 and 3
  15. and ind_pad = rpad('x',40)
  16. and n2 = 2
  17. ;
  18. Execution Plan (8.1.7.4)
  19. ----------------------------------------------------------
  20. 0 SELECT STATEMENT Optimizer=ALL_ROWS (Cost=264 Card=82 Bytes=4756)
  21. 1 0 TABLE ACCESS (BY INDEX ROWID) OF 'T1' (Cost=264 Card=82 Bytes=4756)
  22. 2 1 INDEX (RANGE SCAN) OF 'T1_I1' (NON-UNIQUE) (Cost=184 Card=82)
  23. Execution Plan (9.2.0.6 and 10.1.0.4)
  24. ----------------------------------------------------------
  25. 0 SELECT STATEMENT Optimizer=ALL_ROWS (Cost=264 Card=82 Bytes=4756)
  26. 1 0 TABLE ACCESS (BY INDEX ROWID) OF 'T1' (Cost=264 Card=82 Bytes=4756)
  27. 2 1 INDEX (RANGE SCAN) OF 'T1_I1' (NON-UNIQUE) (Cost=184 Card=1633)

  28. The alter session command is there for the benefit of 9i and 10g. The unhinted execution
  29. plan was a full tablescan, but when I first put in an index hint, the optimizer insisted on using
  30. the index skip scan mechanism, and in 10g if I then included the no_index_ss() hint, the index
  31. was disabled and the plan went back to a tablescan (I would be inclined to call this behavior a
  32. bug—it seems perfectly reasonable to me to say, “Use this index, but don’t do a skip scan,” but
  33. it is possible that it’s the specified behavior).
复制代码

使用道具 举报

回复
论坛徽章:
30
ITPUB元老
日期:2005-02-28 12:57:00ITPUB十周年纪念徽章
日期:2011-11-01 16:19:41管理团队成员
日期:2011-05-07 01:45:082010数据库技术大会纪念徽章
日期:2010-05-13 09:34:23数据库板块每日发贴之星
日期:2006-06-21 01:01:30数据库板块每日发贴之星
日期:2006-06-12 01:01:37会员2006贡献徽章
日期:2006-04-17 13:46:34数据库板块每日发贴之星
日期:2005-12-03 01:01:33授权会员
日期:2005-10-30 17:05:33ITPUB社区OCM联盟徽章
日期:2014-04-01 13:07:37
7#
发表于 2011-10-10 13:34 | 只看该作者
统计值不全或某些bug也会导致类似现象发生,应用是否使用了绑定变量?语句是否有多个执行计划,使用select * from table(dbms_xplan.display_awr('sqlid'));看一下是不是有多个plan,如果是的话,可能是由于bind peaking特性导致,可以grant select on xxx to public再revoke重新生成执行计划,不过如果业务比较忙的时候可能还是不顶用的。

使用道具 举报

回复
论坛徽章:
1
ITPUB十周年纪念徽章
日期:2011-11-01 16:23:26
8#
 楼主| 发表于 2011-10-10 13:36 | 只看该作者
nmgzw 发表于 2011-10-10 08:25

查了一些资料也有人提到说10g CBO比较倾向于index skip scan是一个bug,说是在11g已经解决了,但是我现在还不能在生产上直接把index skip scan参数调整为false,因为其他有的地方会用到,之前也试过在这句sql上加no_index_ss,效果和你描述的一样,CBO会选择走table full scan而不是走index range scan,不知道有没有其他方法可以解决这个问题。

使用道具 举报

回复
论坛徽章:
1
ITPUB十周年纪念徽章
日期:2011-11-01 16:23:26
9#
 楼主| 发表于 2011-10-10 13:40 | 只看该作者
xccheese 发表于 2011-10-9 23:43
ORACLE官方说,在前导列唯一值较少的情况下,才会用到index skip can。
master_ac_no='123456789012' 这个 ...

我这个表里的前导列是trn_date,索引的blevel是2,trn_date的选择性较低是按月做的分区,master_ac_no有较高的选择性,官方的说法是如果在where条件中没有trn_date的只有master_ac_no的情况下才会走index skip scan,rebuild过最近两个月的分区,然后只是查询这两个月的交易还是走的是skip scan。

使用道具 举报

回复
论坛徽章:
138
19周年集字徽章-19
日期:2020-06-08 08:30:56马上加薪
日期:2014-02-19 11:55:14马上有对象
日期:2014-02-19 11:55:14马上有钱
日期:2014-02-19 11:55:14马上有房
日期:2014-02-19 11:55:14马上有车
日期:2014-02-19 11:55:14马上有房
日期:2014-02-18 16:42:022014年新春福章
日期:2014-02-18 16:42:02路虎
日期:2013-11-22 12:26:18问答徽章
日期:2014-05-08 12:15:31
10#
发表于 2011-10-10 13:56 | 只看该作者
select /*+ index_rs(inct) */ * from inct where master_ac_no='123456789012' and trn_date>=to_date('20110801','yyyymmdd') and trn_date<=to_date('20111001','yyyymmdd');

看看

使用道具 举报

回复

您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

TOP技术积分榜 社区积分榜 徽章 团队 统计 知识索引树 积分竞拍 文本模式 帮助
  ITPUB首页 | ITPUB论坛 | 数据库技术 | 企业信息化 | 开发技术 | 微软技术 | 软件工程与项目管理 | IBM技术园地 | 行业纵向讨论 | IT招聘 | IT文档
  ChinaUnix | ChinaUnix博客 | ChinaUnix论坛
CopyRight 1999-2011 itpub.net All Right Reserved. 北京盛拓优讯信息技术有限公司版权所有 联系我们 未成年人举报专区 
京ICP备16024965号-8  北京市公安局海淀分局网监中心备案编号:11010802021510 广播电视节目制作经营许可证:编号(京)字第1149号
  
快速回复 返回顶部 返回列表