表t_busi_main_presend2建了索引T_BUSI_MAIN_PRESEND2_SHSTATUS在SHSTATUS欄位,SHSTATUS char(1) default '0',只有2個值 '0' ,'1'。初始值為‘0’,處理之後為‘1’,表中幾十萬資料,大部分為‘1’,現在有8條為‘0’。
現在,建索引(類型為normal,不能bitmap,會鎖)後,下面語句竟然是全表!
select * from t_busi_main_presend2 where shstatus='0'
於是,我:
1.重新分析表之後繼續執行,還是不行:
analyze table t_busi_main_presend2 compute statistics;
2.重建索引,仍然不行:
alter index T_BUSI_MAIN_PRESEND2_SHSTATUS rebuild;
3.清空shar pool還是不行:
alter system flush shared_pool
這三種都不行,就先刪除表的統計,然後不要分析表,再看看走不走索引:
begin DBMS_STATS.delete_table_stats(ownname => 'YDSOFT_TEST',tabname => 'T_MT'); end;
我自己這樣之後,走索引了。
另外,在PL/SQL中用F5是看不到執行計畫的 統計資訊的,
select * from table ( dbms_xplan.display_cursor('SQL_ID')) 這種方法能看到
sql_id 自己到 V$SQL 裡面撈去,或者到em中看
經過高人指點,有一下幾種方案:
2.一般可行的方法:
1.由於該欄位1值很多,0值很少,那麼
①先刪除之前該索引的統計資訊
②按表數量的1%來採樣收集統計資訊
採樣後:
查1的,走全表;查0的,走索引('YDSOFT_TEST'是owner。注意收集1%那麼下面ESTIMATE_PERCENT=>1後面不能要%,否則會
ORA-06550: 第 2 行, 第 114 列:
PLS-00103: 出現符號 "%"在需要下列之一時:
) , * & = - + < / > at in is
mod remainder not rem <an exponent (**)> <> or != or ~= >= <=
<> and or like LIKE2_ LIKE4_ LIKEC_ between || multiset
member SUBMULTISET_
符號 "%" 被忽略。
)。這是正確的結果:
參數解釋:
'YDSOFT_TEST'是owner
cascade=true表示
ESTIMATE_PERCENT=>1 索引也做分析這裡的百分比是約小越好,中間原因太複雜了,沒聽老師講明白。“桶”那個問題(在下面),不太明白。
method_opt 是表關聯分析
第一句是刪除索引的統計
SQL> begin 2 DBMS_STATS.delete_index_stats(ownname => 'YDSOFT_TEST',indname => 'T_BUSI_MAIN_PRESEND2_SHSTATUS'); 3 end; 4 /
beginDBMS_STATS.GATHER_TABLE_STATS('YDSOFT_TEST', 'T_BUSI_MAIN_PRESEND2', DEGREE=>3, CASCADE=>TRUE,ESTIMATE_PERCENT=>1 ,no_invalidate => false);end;
2.此方法對於自動執行的系統中不太實用,但是自己手動操作一些東西的時候還是可以用的
在pl/sql“解釋計劃視窗”中,選擇 “最佳化器目標”(選擇/規則/第一行/所有行),分別選,看哪個走索引,最後確定 規則/第一行 走索引,此時可以加 /*+rule*/ 使其強制走索引。
select /*+rule*/* from t_busi_main_presend2 where shstatus='0'update /*+rule*/t_busi_main_presend2 set shstatus='1' where shstatus='0' and id<>'504808'
筆記,關於採樣量:
採樣越大,是因為不同值太多
值太多,反而值越小越好就把它看成個廠房的空間吧如果你有3個值,只需要2個桶就夠了,打個比方比如值為1,佔比90%,那不為1人只佔10%,當然走索引了
當然,這裡的桶不存資料,只存資料規模也就是說產生插計劃的時候,先判斷是否有HINT,再看錶規模,再看資料長條圖中來判斷目標資料的規模其實就是資料分布比如1值佔比,資料分散性
這個和IO都是相尖的
相關
長條圖,一是資料佔比,二是資料分散性的一個指標
高度還沒看
掃描 數字越大越快,不是指表分析,是全表取樣掃描。我特指這種情況,不是表分析。
select * from tablename sample(95) order by rowid desc;
備忘:此語句sample後面跟的數字越大,掃描速度越快。
以上語句,從一個很大的表中,快速掃描到 最後插入的資料,非常有效。【其實這個也是基於,表分析的結果,篩選的】