SELECTIVITY 選擇率討論

選擇性(SELECTIVITY)這個是個老話題了,作優化的DBA確定聽過。數據庫

在說這個選擇率以前須要澄清幾個概念:測試

基數(CARDINALITY)

某個列惟一鍵(Distinct_Keys)的數量叫做基數。主鍵列的基數等於表的總行數。基數的高低影響列的數據分佈。優化

以測試表test爲例,owner列和object_id列的基數分別以下所示。spa

select count(distinct owner),count(distinct object_id),count(*) from test;
 COUNT(DISTINCT OWNER) COUNT(DISTINCT OBJECT_ID)   COUNT(*)
-------------------- ------------------------ ----------
                  29                    72462      72462

咱們能夠看到 object_id 列基數比較高,因此它的數據分佈比較均勻,code

選擇性(SELECTIVITY)

基數與總行數的比值再乘以100%就是某個列的選擇性。索引

SELECTIVITY = CARDINALITY/total_rows *100%  也就是 選擇率 = 基數/表總行數 *100%

如今來構造數據測試一下:it

create table test as select * from dba_objects;

--收集 SYS.TEST統計信息,否則 ‘dba_tab_col_statistics’會沒有SYS.TABLE的統計信息。
BEGIN
   DBMS_STATS.GATHER_TABLE_STATS(ownname          => 'SYS',
                                 tabname          => 'TEST',
                                 estimate_percent => 100,
                                 method_opt => 'for all columns size 1',
                                 no_invalidate    => FALSE,
                                 degree           => 1,
                                 cascade          => TRUE);
 END;
 /


--刷新數據庫信息,避免干擾。也能夠不作
begin
   dbms_stats.flush_database_monitoring_info;
  end;
 /


--查看SYS.TEST 各個列的選擇率
select a.table_name,a.column_name,
          b.num_rows,
          a.num_distinct Cardinality,
          round(a.num_distinct / b.num_rows * 100, 2) selectivity,
          a.histogram,
          a.num_buckets
     from dba_tab_col_statistics a, dba_tables b
    where a.owner = b.owner
      and a.table_name = b.table_name
     and a.owner = 'SYS'
    and a.table_name = 'TEST';

查看 ‘selectivity’列 >20%的適合建立索引。table

相關文章
相關標籤/搜索