Oracle的基数与选择性

基数

 

    一个列中唯一键(Distinct_keys)的个数,如有一个100W行的表,性别列的基数为2 (select distinct gender from test),主键列的基数为100W(select distinct mid from test);

 

选择性

 

    基数/总行数所占的百分比,性别 2/100w * 100% 主键 100%  选择性越高 越有利于使用索引 20~30%就算是比较高了

 

1、如何判断是一个索引创建的是好还是坏呢? 

 

     就看他的基数和选择性 如果基数大选择性大 那么使用索引就比较好

 

2、性别这个列使不使用索引?

 

要看情况:

从OLTP 系统上来说 在选择性低的列上创建索引肯定不适合的,基数/选择性高的列,适合建立B-Tree索引;

    在OLAP系统中基数低的列根据需求,有可能会建立bitmap索引

 

3、如何查看列的选择性和基数呢?

 

创建一个test测试表,

create table test as select * from dba_objects;  

create index idx_owner on test(owner);    

create index idx_object_name on test(object_name);

查看owner列和object_name列的基数

select count(distinct owner),count(distinct object_name) from test;

查看列的基数和选择性,可以使用如下脚本

select count(distinct column_name),count(*) total_rows,count(distinct column_name) / count(*) * 100 selectivity from table_name;  

 

我们查看test表的owner的基数和选择性

select ,count(*) total_rows,count(distinct owner) / count(*) * 100 selectivity from test;

count(distinct owner)列为基数

total_rows列为总行数

selectivity列为选择性

 

在做SQL优化的时候,不要急忙运行上面SQL,首先应该检查表的segment_size有多大,如果表的segment_size过大(比如超过SGA的buffer_cache),你要考虑运行上面SQL

是否对你当前的系统有影响,如果是测试环境,无所谓,如果是生产环境,要小心谨慎。

--其实建议使用统计信息表(dba_tab_col_statistics 、dba_tables )里的信息来查看选择性和基数,这里注意我们首先要收集统计信息,否则返回的列是空值。

select 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 = upper('&owner')

and a.table_name = upper('&table_name')

and a.column_name = upper('&column_name');

 

4、找出系统某个用户中不合理(选择性很低)的索引脚本

 

select a.OWNER,

a.INDEX_NAME,

a.TABLE_NAME,

a.DISTINCT_KEYS Cardinality,

a.NUM_ROWS,

round(a.DISTINCT_KEYS / NUM_ROWS * 100, 2) selectivity

from dba_ind_statistics a

where A.OWNER = upper('&owner');

selectivity <5 一般选择性小于5% 就属于选择性差

 

如果统计信息有可能不是最新的 最好使用下面的语句

select table_name,index_name,round(distinct_keys/num_rows * 100, 2) selectivity from user_indexes;

但是选择性低的列也不一定不需要建索引 要根据业务来 比如有7W行记录 SCOTT的有23行 如果经常根据SCOTT查 要建立索引

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值