ITPub博客

首页 > Linux操作系统 > Linux操作系统 > 为什么进行统计分析执行效率反而更差呢?

为什么进行统计分析执行效率反而更差呢?

原创 Linux操作系统 作者:yezhibin 时间:2009-09-02 13:07:04 0 删除 编辑
  有一个经典案例,在8i到10g版本中,我们执行统计分析后,感觉执行效率反而更差了,造成该原因是我们创建了一个function-based index,将会产生一个隐藏列,该隐藏列会参与到成本计算。

 具体的实验如下:

1、创建测试表
SQL> create table t1
            as select 'a' col1, rpad('x', 200) col2 from all_objects where rownum<=100
  
SQL>insert into t1  select  'b' col1, rpad('x', 200) col2 from all_objects where  rownum<=10000;
  
SQL>create index t1_idx on t1 (upper(col1));

2、统计分析后进行检测:

  SQL>exec dbms_stats.gather_table_stats(user, 't1', cascade=>true);
  
  SQL>explain plan for select * from t1 where upper(col1)='A';
  
  SQL>select * from table(dbms_xplan.display);

--------------------------------------------------------------------------
| Id  | Operation         | Name | Rows  | Bytes | Cost (%CPU)| Time     |
--------------------------------------------------------------------------
|   0 | SELECT STATEMENT  |      |  5050 |  1001K|    70   (2)| 00:00:01 |
|*  1 |  TABLE ACCESS FULL| T1   |  5050 |  1001K|    70   (2)| 00:00:01 |
--------------------------------------------------------------------------

10053跟踪文件如下:

SINGLE TABLE ACCESS PATH
Column (#3): SYS_NC00003$(CHARACTER)
    AvgLen: 2.00 NDV: 2 Nulls: 0 Density: 0.5

  Table: T1  Alias: T1
    Card: Original: 10100  Rounded: 5050  Computed: 5050.00  Non Adjusted: 5050.00
  Access Path: TableScan
    Cost:  69.77  Resp: 69.77  Degree: 0
      Cost_io: 69.00  Cost_cpu: 7351525
      Resp_io: 69.00  Resp_cpu: 7351525
  Access Path: index (AllEqRange)
    Index: T1_IDX
    resc_io: 159.00  resc_cpu: 3001659
    ix_sel: 0.5  ix_sel_with_filters: 0.5
    Cost: 159.31  Resp: 159.31  Degree: 1
  Best:: AccessPath: TableScan
         Cost: 69.77  Degree: 1  Resp: 69.77  Card: 5050.00  Bytes: 0

以上是隐藏列SYS_NC00003$被统计分析。
该隐藏列参与的CBO的成本计算,在计算CBO的时候全表扫描cost=69.77,而走索引的cost=159.31,所以选择全表扫描

3、删除索引和统计分析


SQL>exec dbms_stats.delete_table_stats(user, 't1');
SQL>explain plan for select * from t1 where upper(col1)='A';
SQL>select * from table(dbms_xplan.display);
  --------------------------------------------------------------------------------------
| Id  | Operation                   | Name   | Rows  | Bytes | Cost (%CPU)| Time     |
--------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT            |        |   101 | 20503 |    11   (0)| 00:00:01 |
|   1 |  TABLE ACCESS BY INDEX ROWID| T1     |   101 | 20503 |    11   (0)| 00:00:01 |
|*  2 |   INDEX RANGE SCAN          | T1_IDX |    40 |       |     9   (0)| 00:00:01 |
--------------------------------------------------------------------------------------

感觉是删除了统计统计分析造成效率更高,其实不是,以下实验是屏蔽掉隐藏列的统计分析。

SQL>drop index t1_idx;

SQL>exec dbms_stats.gather_table_stats(user, 't1', cascade=>true);

SQL>create index t1_idx on t1 (upper(col1));

SQL>exec dbms_stats.gather_index_stats(user, 't1_idx');

SQL>explain plan for select * from t1 where upper(col1)='A';

SQL>select * from table(dbms_xplan.display);
--------------------------------------------------------------------------------------
| Id  | Operation                   | Name   | Rows  | Bytes | Cost (%CPU)| Time     |
--------------------------------------------------------------------------------------
|   0 | SELECT STATEMENT            |        |   101 | 20503 |    11   (0)| 00:00:01 |
|   1 |  TABLE ACCESS BY INDEX ROWID| T1     |   101 | 20503 |    11   (0)| 00:00:01 |
|*  2 |   INDEX RANGE SCAN          | T1_IDX |    40 |       |     9   (0)| 00:00:01 |
--------------------------------------------------------------------------------------

10053 trace 文件:
SINGLE TABLE ACCESS PATH
  Column (#3): SYS_NC00003$(CHARACTER)  NO STATISTICS (using defaults)
    AvgLen: 1.00 NDV: 316 Nulls: 0 Density: 0.0031683

  Table: T1  Alias: T1
    Card: Original: 10100  Rounded: 101  Computed: 101.00  Non Adjusted: 101.00
  Access Path: TableScan
    Cost:  69.76  Resp: 69.76  Degree: 0
      Cost_io: 69.00  Cost_cpu: 7252545
      Resp_io: 69.00  Resp_cpu: 7252545
  Access Path: index (AllEqGuess)
    Index: T1_IDX
    resc_io: 11.00  resc_cpu: 94356
    ix_sel: 0.004  ix_sel_with_filters: 0.004
    Cost: 11.01  Resp: 11.01  Degree: 1
  Best:: AccessPath: IndexRange  Index: T1_IDX
         Cost: 11.01  Degree: 1  Resp: 11.01  Card: 101.00  Bytes: 0

注意一点隐藏列没有被统计分析,他采用缺省值,Density=0.0031683,造成参与成本计算的时候,全表扫描成本是69.76,索引的成本扫描只有11.01。

来自 “ ITPUB博客 ” ,链接:https://blog.itpub.net/354732/viewspace-613784/ ,如需转载,请注明出处,否则将追究法律责任。

下一篇: Index rebuild --case 1
请登录后发表评论 登录
全部评论

注册时间:2008-12-18

  • 博文量
    159
  • 访问量
    559686