还是接着前天的关于执行计划触发bug的研究:
前天说了可以尝试重新收集统计信息,重新创建表等方式进行对语句执行计划的修改。
今天说干就干,执行
EXEC DBMS_STATS.gather_table_stats(ownname => 'AUTOCLAIM',tabname => UPPER('lp_flow_state'),estimate_percent => 80,method_opt=> 'for all indexed columns',cascade=>true,degree => 2);
以及其他几个表的统计信息一并重新收集了下,但是发现执行计划仍然没有变(通过toad查看执行计划的方式查看)
更郁闷的是,居然在v$sql_plan中无法查找到对应的语句。
怎么回事呢?不是说对语句中的对象做个ddl ;重新收集统计信息就可以重新生成执行计划吗?难道是这个执行计划真是最优的?
但从实际角度看,肯定是不对的。找动态视图没有查找到这个信息就更怪了。
难道我的理论存在一个很大的错误?原来我一直认为查看执行计划后,在共享池就存在执行计划了。
如果是非要语句执行后,才会产生执行计划到共享池,那么我遇到的问题就不是问题,而且纠正了我一直存在的理解误差。
那么来进行一下验证:
select * from t1;(只查看执行计划)
select * from v$sql where sql_text like 'select * from t1%'
----没有结果
select * from t1;(实际执行)
select * from v$sql where sql_text like 'select * from t1%'
----存在结果。
简单的测试,就纠正了原来存在的误差。
带来一个新问题,如果我们现在发现语句执行计划由于绑定变量最初带入的变量值存在严重的问题,想清除掉这个执行计划。让它在带入合适的绑定变量进行执行计划的生成?
查看网络上的信息,棉花糖的一篇文章给了一些帮助。
select * from v$sql where sql_text like 'select * from t1%'
----查出sql地址和hash_value
exec sys.dbms_shared_pool.purge('0700000A0D2C7DC8,1468955422','C'); ---前面是地址,后面是hash_value
查看 select * from v$sql where sql_text like 'select * from t1%'
仍然存在记录。
原来还要设置一个事件才可以触发:
alter session set events '5614566 trace name context forever';
再执行exec sys.dbms_shared_pool.purge('0700000A0D2C7DC8,1468955422','C');
select * from v$sql where sql_text like 'select * from t1%'
不存在记录,操作生效了。
来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/288166/viewspace-706304/,如需转载,请注明出处,否则将追究法律责任。
转载于:http://blog.itpub.net/288166/viewspace-706304/