【性能优化】之 BITMAP 及分区表 的演示

以下演示有两个重点:


1.BITMAP索引的局限性:  DML操作导致位图索引锁定

2.分区索引的性能并没有比全局索引更优。



书面作业,必须给出全部的演示过程。<br>

1.分别给出一个B-tree索引针对全表扫描性能高和低的例子。<br>
2.分别给出一个Bitmap索引针对b-tree索引性能高和低的例子。<br>
3.演示DML操作导致位图索引锁定示例。<br>
4.创建一个全文索引,比较它和传统的模糊查询的性能。<br>
5.分别演示分区索引的性能优化全局索引和差于全局索引的示例,并分析原因。<br>





====================================================================================
1.分别给出一个B-tree索引针对全表扫描性能高和低的例子。<br>

答:

    延用上课使用的环境,表T 中的OBJECT_ID 中建有索引,现在使用两种方法进行查询:

    1.1.1 使用索引查询
    SQL> explain plan for select *  from t where object_id=100;
    Explained

    SQL> select * from table(dbms_xplan.display(null,null,'typical'));
    PLAN_TABLE_OUTPUT
    --------------------------------------------------------------------------------
    Plan hash value: 514881935
    --------------------------------------------------------------------------------
    | Id  | Operation                   | Name     | Rows  | Bytes | Cost (%CPU)| Ti
    --------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT            |          |    63 |  6111 |    67   (0)| 00
    |   1 |  TABLE ACCESS BY INDEX ROWID| T        |    63 |  6111 |    67   (0)| 00
    |*  2 |   INDEX RANGE SCAN          | IDX_T_ID |    63 |       |     3   (0)| 00
    --------------------------------------------------------------------------------
    Predicate Information (identified by operation id):
    ---------------------------------------------------
       2 - access("OBJECT_ID"=100)
    14 rows selected

    1.1.2 使用HINT 指定使用全表搜索查询
    SQL> explain plan for select /*+FULL(T)*/ *  from t where object_id=100;
    Explained

    SQL> select * from table(dbms_xplan.display(null,null,'typical'));
    PLAN_TABLE_OUTPUT
    --------------------------------------------------------------------------------
    Plan hash value: 1601196873
    --------------------------------------------------------------------------
    | Id  | Operation         | Name | Rows  | Bytes | Cost (%CPU)| Time     |
    --------------------------------------------------------------------------
    |   0 | SELECT STATEMENT  |      |    63 |  6111 | 28636   (1)| 00:05:44 |
    |*  1 |  TABLE ACCESS FULL| T    |    63 |  6111 | 28636   (1)| 00:05:44 |
    --------------------------------------------------------------------------
    Predicate Information (identified by operation id):
    ---------------------------------------------------
       1 - filter("OBJECT_ID"=100)
    13 rows selected



    从以上执行计划的成本 可以看到,索引搜索是全表搜索的1/400以上;


    1.2 再看一个使用索引的性能比全表搜索差的演示:
        
        建立一个索引
        create index idx_t_status on t(status);


    1.2.1 查询表中object_id<=100 (基本上是全表数据一起查询了)

        1.2.2 按索引查询

        SQL> explain plan for select /*+ index(t idx_t_status)*/ * from T  WHERE status ='VALID';
        Explained

        SQL> select * from table(dbms_xplan.display(null,null,'typical'));
        PLAN_TABLE_OUTPUT
        --------------------------------------------------------------------------------
        Plan hash value: 709710412
        --------------------------------------------------------------------------------
        | Id  | Operation                   | Name         | Rows  | Bytes | Cost (%CPU)
        --------------------------------------------------------------------------------
        |   0 | SELECT STATEMENT            |              |  2432K|   224M| 40808   (1)
        |   1 |  TABLE ACCESS BY INDEX ROWID| T            |  2432K|   224M| 40808   (1)
        |*  2 |   INDEX RANGE SCAN          | IDX_T_STATUS |  2432K|       |  5792   (1)
        --------------------------------------------------------------------------------
        Predicate Information (identified by operation id):
        ---------------------------------------------------
           2 - access("STATUS"='VALID')
        14 rows selected


        1.2.3 没有指定使用索引,系统自动进行了全表搜索

        SQL> explain plan for select * from T  WHERE status ='VALID';
        Explained

        SQL> select * from table(dbms_xplan.display(null,null,'typical'));
        PLAN_TABLE_OUTPUT
        --------------------------------------------------------------------------------
        Plan hash value: 1601196873
        --------------------------------------------------------------------------
        | Id  | Operation         | Name | Rows  | Bytes | Cost (%CPU)| Time     |
        --------------------------------------------------------------------------
        |   0 | SELECT STATEMENT  |      |  2432K|   224M| 28676   (1)| 00:05:45 |
        |*  1 |  TABLE ACCESS FULL| T    |  2432K|   224M| 28676   (1)| 00:05:45 |
        --------------------------------------------------------------------------
        Predicate Information (identified by operation id):
        ---------------------------------------------------
           1 - filter("STATUS"='VALID')
        13 rows selected

        SQL>

        从上面演示可以看出,没有使用索引的执行计划反而比使用了索引更优。是因为status ='VALID'
        的选择性并不高,基本上所有数据都满足此条件。


****************************************************************************************************
2.分别给出一个Bitmap索引针对b-tree索引性能高和低的例子。<br>

    再延用上面的数据示例,使用索引查询所有状态为status ='VALID' 的总数。
    看到这时的执行成本 为: 5792

    SQL> explain plan for select /*+ index(t idx_t_status)*/  count(0) from T  WHERE status ='VALID';
    Explained

    SQL> select * from table(dbms_xplan.display(null,null,'typical'));
    PLAN_TABLE_OUTPUT
    --------------------------------------------------------------------------------
    Plan hash value: 1684240785
    --------------------------------------------------------------------------------
    | Id  | Operation         | Name         | Rows  | Bytes | Cost (%CPU)| Time
    --------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT  |              |     1 |     7 |  5792   (1)| 00:01:10
    |   1 |  SORT AGGREGATE   |              |     1 |     7 |            |
    |*  2 |   INDEX RANGE SCAN| IDX_T_STATUS |  2432K|    16M|  5792   (1)| 00:01:10
    --------------------------------------------------------------------------------
    Predicate Information (identified by operation id):
    ---------------------------------------------------
       2 - access("STATUS"='VALID')
    14 rows selected

    SQL>




    在表T 中,删除上一个索引,另外建立一个bitmap索引:

    create Bitmap index idx_t_status on t(status);


    SQL> explain plan for select count(0) from T where status ='VALID';
    Explained

    SQL> select * from table(dbms_xplan.display(null,null,'typical'));
    PLAN_TABLE_OUTPUT
    --------------------------------------------------------------------------------
    Plan hash value: 1122805388
    --------------------------------------------------------------------------------
    | Id  | Operation                   | Name         | Rows  | Bytes | Cost (%CPU)
    --------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT            |              |     1 |     7 |    61   (0)
    |   1 |  SORT AGGREGATE             |              |     1 |     7 |
    |   2 |   BITMAP CONVERSION COUNT   |              |  2432K|    16M|    61   (0)
    |*  3 |    BITMAP INDEX SINGLE VALUE| IDX_T_STATUS |       |       |
    --------------------------------------------------------------------------------
    Predicate Information (identified by operation id):
    ---------------------------------------------------
       3 - access("STATUS"='VALID')
    15 rows selected

    SQL>

    这时,系统自动走了BITMAP 索引,这时的执行成本 只有 61.优势明显。

****************************************************************************************************

3.演示DML操作导致位图索引锁定示例。<br>

    3.1 建立示例数据
    create table t2 as
    SELECT OBJECT_ID FROM T
    WHERE OBJECT_ID<10

    insert into t2
    SELECT OBJECT_ID FROM T
    WHERE OBJECT_ID<10



    select object_id,count(0) from t2
    group by object_id

        OBJECT_ID    COUNT(0)
        ---------------------------
        2    960
        3    960
        4    960
        5    960
        6    960
        7    960
        8    960
        9    960


    3.2建立bitmap 索引

    create bitmap index  idx_t2_id on t2(object_id);


    3.3 测试BITMAP 锁机制
    
    3.3.1 在一个窗口中修改数据,把 object_id in (2,3,4) 修改为1

    SQL> select distinct sid from v$mystat s;
           SID
    ----------
            92

    SQL> update t2 set object_id=1 where object_id in (2,3,4);
    2880 rows updated

    SQL>

    3.3.2 再开3个窗口,插入OBJECT_ID 为2,3,4 的数据,看到,都已处在锁状态

    SQL> select distinct sid from v$mystat s;
           SID
    ----------
            24

    SQL> insert into t2 values(2);



    SQL> select distinct sid from v$mystat s;
           SID
    ----------
           103

    SQL> insert into t2 values(3);

    SQL> select distinct sid from v$mystat s;
           SID
    ----------
           146

    SQL> insert into t2 values(4);


    再开一个窗口,把object_id =5 的也修改成1,这时看到,也是阻塞状态
    SQL> select distinct sid from v$mystat s;
           SID
    ----------
           157

    SQL>  update t2 set object_id=1 where object_id =5;


    我们再查询表:V$LOCK;
    SELECT * FROM V$LOCK L WHERE L.TYPE IN ('TX','TM');

        ADDR                KADDR                SID    TYPE    ID1        ID2        LMODE    REQUEST    CTIME    BLOCK
    1    00000002B13B6190    00000002B13B61E8    146    TX        655364    198442    0        4        430        0
    2    00000002B13B66E8    00000002B13B6740    103    TX        655364    198442    0        4        448        0
    3    00000002B13BD508    00000002B13BD560    157    TX        655364    198442    0        4        254        0
    4    00000002B13BD968    00000002B13BD9C0    24    TX        655364    198442    0        4        455        0
    5    0000000015FC4270    0000000015FC42D0    157    TM        94186    0        3        0        254        0
    6    0000000015FC4270    0000000015FC42D0    146    TM        94186    0        3        0        430        0
    7    0000000015FC4270    0000000015FC42D0    24    TM        91329    0        3        0        1437    0
    8    0000000015FC4270    0000000015FC42D0    24    TM        94186    0        3        0        455        0
    9    0000000015FC4270    0000000015FC42D0    103    TM        94186    0        3        0        448        0
    10    0000000015FC4270    0000000015FC42D0    92    TM        94186    0        3        0        479        0
    11    00000002A9EB3090    00000002A9EB3108    157    TX        458765    11761    6        0        254        0
    12    00000002A8D0A528    00000002A8D0A5A0    146    TX        589855    74744    6        0        430        0
    13    00000002A9EED250    00000002A9EED2C8    24    TX        65539    10414    6        0        1437    0
    14    00000002A9EF1A28    00000002A9EF1AA0    103    TX        262165    10701    6        0        448        0
    15    00000002A8D15D18    00000002A8D15D90    92    TX        655364    198442    6        0        479        1


    可以看到第15条记录中,进程92有一个锁,
    1-4记录中的 146,103,157,24 进程,都在等待申请中。

    这就证明,位图索引在修改中,会把相同的索引段都加锁,而其它的相同索引段的对应操作(添加,修改)都会被阻塞。




****************************************************************************************************
4.创建一个全文索引,比较它和传统的模糊查询的性能。<br>

    4.1 测试环境
    select count(0) from  company
    union all
    select count(0) from  company_text_idx

    COUNT(0)
    -----------
    9999
    9999

    4.2 在传统表中建立索引
    create index idx_name on company(name);    

    4.3 在全文索引测试表中建立全文索引
    
    BEGIN
      ctx_ddl.create_preference ('my_lexer', 'chinese_vgram_lexer');
    END;
/
    CREATE INDEX  idx_comp_text_idx ON company_text_idx(name) indextype is ctxsys.context parameters('lexer my_lexer');


    4.4全文搜索执行计划:
        从执行计划中可以看到,查询9条记录,成本 为:6;字节为 79130k,唯一性读为:473

        SQL> select * from company_text_idx where contains(name,'王飞')>0;

        已选择9行。

        执行计划
        ----------------------------------------------------------
        Plan hash value: 3789291194

        ---------------------------------------------------------------------------------------------------
        | Id  | Operation                   | Name                | Rows  | Bytes | Cost (%CPU)| Time     |
        ---------------------------------------------------------------------------------------------------
        |   0 | SELECT STATEMENT            |                     |     5 | 79130 |     6   (0)| 00:00:01 |
        |   1 |  TABLE ACCESS BY INDEX ROWID|    COMPANY_TEXT_IDX |     5 | 79130 |     6   (0)| 00:00:01 |
        |*  2 |   DOMAIN INDEX              | IDX_COMP_TEXT_IDX   |       |       |     4   (0)| 00:00:01 |
        ---------------------------------------------------------------------------------------------------

        Predicate Information (identified by operation id):
        ---------------------------------------------------

           2 - access("CTXSYS"."CONTAINS"("NAME",'王飞')>0)

        Note
        -----
           - dynamic sampling used for this statement (level=2)


        统计信息
        ----------------------------------------------------------
                137  recursive calls
                  0  db block gets
                473  consistent gets
                  0  physical reads
                  0  redo size
              34324  bytes sent via SQL*Net to client
              22618  bytes received via SQL*Net from client
                 78  SQL*Net roundtrips to/from client
                  0  sorts (memory)
                  0  sorts (disk)
                  9  rows processed

    4.5传统计索引搜索计划:
        执行成本 为9,唯一性读为91,字节为 138K,
        成本比全文搜索差一些。但读取的字节数少,唯一性读也少。从这里也可以看到,全文检索使用了更大的存储空间。


        SQL> select * from  company where name like '王飞%';

        已选择9行。


        执行计划
        ----------------------------------------------------------
        Plan hash value: 1068597349

        ------------------------------------------------------------------------------------------
        | Id  | Operation                   | Name       | Rows  | Bytes | Cost (%CPU)| Time     |
        ------------------------------------------------------------------------------------------
        |   0 | SELECT STATEMENT            |            |     9 |   138K|     9   (0)| 00:00:01 |
        |   1 |  TABLE ACCESS BY INDEX ROWID|    COMPANY |     9 |   138K|     9   (0)| 00:00:01 |
        |*  2 |   INDEX RANGE SCAN          | IDX_NAME   |     9 |       |     2   (0)| 00:00:01 |
        ------------------------------------------------------------------------------------------

        Predicate Information (identified by operation id):
        ---------------------------------------------------

           2 - access("NAME" LIKE '王飞%')
               filter("NAME" LIKE '王飞%')

        Note
        -----
           - dynamic sampling used for this statement (level=2)


        统计信息
        ----------------------------------------------------------
                  9  recursive calls
                  0  db block gets
                 91  consistent gets
                  0  physical reads
                  0  redo size
              34236  bytes sent via SQL*Net to client
              22618  bytes received via SQL*Net from client
                 78  SQL*Net roundtrips to/from client
                  0  sorts (memory)
                  0  sorts (disk)
                  9  rows processed

        SQL>
    4.6 再换一个传统查询中,包含条件的执行计划。
    这时可以看到,无法使用索引了,成本达到了 254,唯一性读也达到了987。


    SQL> select * from  company where name like '%王飞%';

    已选择9行。


    执行计划
    ----------------------------------------------------------
    Plan hash value: 1376141687

    --------------------------------------------------------------------------------
    | Id  | Operation         | Name       | Rows  | Bytes | Cost (%CPU)| Time     |
    --------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT  |            |    26 |   401K|   254   (0)| 00:00:04 |
    |*  1 |  TABLE ACCESS FULL|    COMPANY |    26 |   401K|   254   (0)| 00:00:04 |
    --------------------------------------------------------------------------------

    Predicate Information (identified by operation id):
    ---------------------------------------------------

       1 - filter("NAME" IS NOT NULL AND "NAME" LIKE '%王飞%')

    Note
    -----
       - dynamic sampling used for this statement (level=2)


    统计信息
    ----------------------------------------------------------
              5  recursive calls
              0  db block gets
            987  consistent gets
              0  physical reads
              0  redo size
          34324  bytes sent via SQL*Net to client
          22618  bytes received via SQL*Net from client
             78  SQL*Net roundtrips to/from client
              0  sorts (memory)
              0  sorts (disk)
              9  rows processed

    SQL>

    从上面的3个执行计划中可以看出,全文检索的性能及搜索灵活性在包含条件下的查询,是更高的。
    但也使用了更多的存储空间。


****************************************************************************************************

5.分别演示分区索引的性能优化全局索引和差于全局索引的示例,并分析原因。<br>(边城日志 2013/11/15 15:50)

    5.1构建演示环境:
    
    在一现有示例表中,基本每月有3000条记录,现另建立表个表,按季度分区保存。

    select to_char(po_dt,'yyyymm') as ym,count(0) from po
    group by to_char(po_dt,'yyyymm')
    order by
    to_char(po_dt,'yyyymm')

        YM    COUNT(0)
        ----------------
    1    201001    3099
    2    201002    2800
    3    201003    3100
    4    201004    3000
    5    201005    3100
    6    201006    3000
    7    201007    3100
    8    201008    3100
    9    201009    3000
    10    201010    3100
    11    201011    3000
    12    201012    3100
    13    201101    3100
    14    201102    2800
    15    201103    3100
    16    201104    3000
    17    201105    1500


    --3个月一个分区
    CREATE TABLE PO_R
   (  POID NUMBER(10,0),
  QTY NUMBER(10,2),
  AMOUNT NUMBER(10,2),
  AUDIT_FLG NUMBER(1,0) DEFAULT 0,
  PO_DT DATE
   )
    PARTITION BY RANGE (PO_DT)
      INTERVAL (NUMTOYMINTERVAL(3, 'MONTH'))
      (PARTITION P1 VALUES LESS THAN (TO_DATE('2010-01-01', 'YYYY-MM-DD')))
      ;

    insert into po_r
    select * from PO
    commit;



    每个分区的数据量
    select t.partition_name,t.num_rows
    from all_tab_partitions t where table_name='PO_R'
    
        PARTITION_NAME    NUM_ROWS
        -------------------------------
    1    P1    0
    2    SYS_P141    8999
    3    SYS_P142    9100
    4    SYS_P143    9200
    5    SYS_P144    9200
    6    SYS_P145    9000
    7    SYS_P146    4500



    5.2.我用两种索引来进行对比:

    5.2.1 全局索引
    create index IDX_PO_R_ID_GLOBAL on PO_R (poid);

    5.2.2 分区索引
    create index IDX_PO_R_ID_LOCAL on PO_R (POID)
      local;
    
    以下为两次不同索引下的执行计划:
    全局索引:成本:1869,唯一性读2403,总字节:187K
    分区索引:成本:1871,唯一性读2412,总字节:187K

    对比看出,全局索引稍胜于分区索引

    SQL> set autotrace on
    SQL> set autotrace traceonly

    SQL> select /*+INDEX(p IDX_PO_R_ID_GLOBAL)*/ * from po_r p where poid between 500  and 7900;

    7401 rows selected.


    Execution Plan
    ----------------------------------------------------------
    Plan hash value: 1901754288

    -------------------------------------------------------------------------------------------------------------------------
    | Id  | Operation                          | Name               | Rows  | Bytes | Cost (%CPU)| Time  | Pstart| Pstop |
    -------------------------------------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT                   |                    |  7402 |   187K|  1868   (1)| 00:00:23 |       |       |
    |   1 |  TABLE ACCESS BY GLOBAL INDEX ROWID| PO_R               |  7402 |   187K|  1868   (1)| 00:00:23 | ROWID | ROWID |
    |*  2 |   INDEX RANGE SCAN                 | IDX_PO_R_ID_GLOBAL |  7402 |       |    21   (0)| 00:00:01 |       |       |
    -------------------------------------------------------------------------------------------------------------------------

    Predicate Information (identified by operation id):
    ---------------------------------------------------

       2 - access("POID">=500 AND "POID"<=7900)


    Statistics
    ----------------------------------------------------------
              1  recursive calls
              0  db block gets
           2403  consistent gets
             19  physical reads
              0  redo size
         231787  bytes sent via SQL*Net to client
           5942  bytes received via SQL*Net from client
            495  SQL*Net roundtrips to/from client
              0  sorts (memory)
              0  sorts (disk)
           7401  rows processed

    SQL> select /*+INDEX(p IDX_PO_R_ID_LOCAL)*/ * from po_r p where poid between 500  and 7900;

    7401 rows selected.


    Execution Plan
    ----------------------------------------------------------
    Plan hash value: 3357987540

    ------------------------------------------------------------------------------------------------------------------------
    | Id  | Operation                          | Name              | Rows  | Bytes | Cost (%CPU)| Time     | Pstart| Pstop |
    ------------------------------------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT                   |                   |  7402 |   187K|  1871   (1)| 00:00:23 |       |       |
    |   1 |  PARTITION RANGE ALL               |                   |  7402 |   187K|  1871   (1)| 00:00:23 |     1 |1048575|
    |   2 |   TABLE ACCESS BY LOCAL INDEX ROWID| PO_R              |  7402 |   187K|  1871   (1)| 00:00:23 |     1 |1048575|
    |*  3 |    INDEX RANGE SCAN                | IDX_PO_R_ID_LOCAL |  7402 |       |    24   (0)| 00:00:01 |     1 |1048575|
    ------------------------------------------------------------------------------------------------------------------------

    Predicate Information (identified by operation id):
    ---------------------------------------------------

       3 - access("POID">=500 AND "POID"<=7900)


    Statistics
    ----------------------------------------------------------
              1  recursive calls
              0  db block gets
           2412  consistent gets
             21  physical reads
              0  redo size
         231787  bytes sent via SQL*Net to client
           5942  bytes received via SQL*Net from client
            495  SQL*Net roundtrips to/from client
              0  sorts (memory)
              0  sorts (disk)
           7401  rows processed

    SQL>    


    5.3再看一个演示,也是全局索引稍胜于分区索引

    SQL> select /*+INDEX(p IDX_PO_R_ID_LOCAL)*/ * from po_r p where poid = 80;


    Execution Plan
    ----------------------------------------------------------
    Plan hash value: 3357987540

    ------------------------------------------------------------------------------------------------------------------------
    | Id  | Operation                          | Name              | Rows  | Bytes | Cost (%CPU)| Time     | Pstart| Pstop |
    ------------------------------------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT                   |                   |     1 |    26 |     9   (0)| 00:00:01 |       |       |
    |   1 |  PARTITION RANGE ALL               |                   |     1 |    26 |     9   (0)| 00:00:01 |     1 |1048575|
    |   2 |   TABLE ACCESS BY LOCAL INDEX ROWID| PO_R              |     1 |    26 |     9   (0)| 00:00:01 |     1 |1048575|
    |*  3 |    INDEX RANGE SCAN                | IDX_PO_R_ID_LOCAL |     1 |       |     8   (0)| 00:00:01 |     1 |1048575|
    ------------------------------------------------------------------------------------------------------------------------

    Predicate Information (identified by operation id):
    ---------------------------------------------------

       3 - access("POID"=80)


    Statistics
    ----------------------------------------------------------
              1  recursive calls
              0  db block gets
             14  consistent gets
              1  physical reads
              0  redo size
            811  bytes sent via SQL*Net to client
            519  bytes received via SQL*Net from client
              2  SQL*Net roundtrips to/from client
              0  sorts (memory)
              0  sorts (disk)
              1  rows processed

    SQL> select /*+INDEX(p IDX_PO_R_ID_GLOBAL)*/ * from po_r p where poid = 80;


    Execution Plan
    ----------------------------------------------------------
    Plan hash value: 1901754288

    -------------------------------------------------------------------------------------------------------------------------
    | Id  | Operation                          | Name               | Rows  | Bytes | Cost (%CPU)| Time  | Pstart| Pstop |
    -------------------------------------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT                   |                    |     1 |    26 |     2   (0)| 00:00:01 |       |       |
    |   1 |  TABLE ACCESS BY GLOBAL INDEX ROWID| PO_R               |     1 |    26 |     2   (0)| 00:00:01 | ROWID | ROWID |
    |*  2 |   INDEX RANGE SCAN                 | IDX_PO_R_ID_GLOBAL |     1 |       |     1   (0)| 00:00:01 |       |       |
    -------------------------------------------------------------------------------------------------------------------------

    Predicate Information (identified by operation id):
    ---------------------------------------------------

       2 - access("POID"=80)


    Statistics
    ----------------------------------------------------------
              1  recursive calls
              0  db block gets
              4  consistent gets
              1  physical reads
              0  redo size
            811  bytes sent via SQL*Net to client
            519  bytes received via SQL*Net from client
              2  SQL*Net roundtrips to/from client
              0  sorts (memory)
              0  sorts (disk)
              1  rows processed

    SQL>
    
    5.4是不是全局索引就一定比分区索引更优呢,下面 我使用PO_DT 字段来建立索引。
    从下面的执行计划中可以看出:
    这时的分区索引是稍优全局索引的。
    所以就性能上来说,并不能武断的说明哪咱索引更优。因为不管是哪种索引,在查询时,都是查询某一段(或一条)。
    然后查询对应一段(或一条)的数据


    SQL> select  * from po_r p where PO_DT=TO_DATE('20100606','YYYYMMDD');

    100 rows selected.


    Execution Plan
    ----------------------------------------------------------
    Plan hash value: 3172462535

    -----------------------------------------------------------------------------------------------------------------------
    | Id  | Operation                          | Name             | Rows  | Bytes | Cost (%CPU)| Time     | Pstart| Pstop |
    -----------------------------------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT                   |                  |   100 |  2600 |     4   (0)| 00:00:01 |       |       |
    |   1 |  PARTITION RANGE SINGLE            |                  |   100 |  2600 |     4   (0)| 00:00:01 |     3 |     3 |
    |   2 |   TABLE ACCESS BY LOCAL INDEX ROWID| PO_R             |   100 |  2600 |     4   (0)| 00:00:01 |     3 |     3 |
    |*  3 |    INDEX RANGE SCAN                | IDX_POR_DT_LOCAL |   100 |       |     1   (0)| 00:00:01 |     3 |     3 |
    -----------------------------------------------------------------------------------------------------------------------

    Predicate Information (identified by operation id):
    ---------------------------------------------------

       3 - access("PO_DT"=TO_DATE(' 2010-06-06 00:00:00', 'syyyy-mm-dd hh24:mi:ss'))


    Statistics
    ----------------------------------------------------------
              1  recursive calls
              0  db block gets
             18  consistent gets
              1  physical reads
              0  redo size
           4026  bytes sent via SQL*Net to client
            585  bytes received via SQL*Net from client
              8  SQL*Net roundtrips to/from client
              0  sorts (memory)
              0  sorts (disk)
            100  rows processed

    SQL> select  * from po_r p where PO_DT=TO_DATE('20100606','YYYYMMDD');

    100 rows selected.


    Execution Plan
    ----------------------------------------------------------
    Plan hash value: 3915168380

    ------------------------------------------------------------------------------------------------------------------------
    | Id  | Operation                          | Name              | Rows  | Bytes | Cost (%CPU)| Time     | Pstart| Pstop |
    ------------------------------------------------------------------------------------------------------------------------
    |   0 | SELECT STATEMENT                   |                   |   100 |  2600 |     5   (0)| 00:00:01 |       |       |
    |   1 |  TABLE ACCESS BY GLOBAL INDEX ROWID| PO_R              |   100 |  2600 |     5   (0)| 00:00:01 |     3 |     3 |
    |*  2 |   INDEX RANGE SCAN                 | IDX_POR_DT_GLOBAL |   100 |       |     1   (0)| 00:00:01 |       |       |
    ------------------------------------------------------------------------------------------------------------------------

    Predicate Information (identified by operation id):
    ---------------------------------------------------

       2 - access("PO_DT"=TO_DATE(' 2010-06-06 00:00:00', 'syyyy-mm-dd hh24:mi:ss'))


    Statistics
    ----------------------------------------------------------
              1  recursive calls
              0  db block gets
             18  consistent gets
              2  physical reads
              0  redo size
           4026  bytes sent via SQL*Net to client
            585  bytes received via SQL*Net from client
              8  SQL*Net roundtrips to/from client
              0  sorts (memory)
              0  sorts (disk)
            100  rows processed

    SQL>


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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值