Pular para o conteúdo

Fóruns Banco de dados Oracle Indice normal ou bitmap? Indice normal ou bitmap?

#88504
Rodrigo Almeida
Participante

    Olá Pessoal,

    Bom! Voltei do almoço e efetuei alguns testes, baseando-se nos conceitos dos índices. O teste é bem simples, mas acho que dá para tirar algum aproveito disso.

    Veja, vamos criar a tabela e a massa de dados:


    SQL> create table TESTE (a number(6), b char(1));

    Tabela criada.

    SQL> declare
    2 contador1 integer;
    3 contador2 integer;
    4 contador3 integer;
    5 contador4 integer;
    6 contador5 integer;
    7 contador6 integer;
    8 contador7 integer;
    9 contador8 integer;
    10 contador9 integer;
    11 begin
    12 contador1 := 1;
    13 contador2 := 10000;
    14 contador3 := 20000;
    15 contador4 := 30000;
    16 contador5 := 40000;
    17 contador6 := 50000;
    18 contador7 := 60000;
    19 contador8 := 70000;
    20 contador9 := 80000;
    21
    22 while contador1 select b, count(b) from teste group by b order by b;

    B COUNT(B)


    N 9999
    S 9999
    1 9999
    2 9999
    3 9999
    4 9999
    5 9999
    6 9999
    7 9999

    9 linhas selecionadas.

    Agora, a criação do índice B*Tree e 2 querys simples.


    SQL> create index idx_b_btree on teste (b);

    ═ndice criado.

    SQL> select count(b) from teste where b = '2';

    COUNT(B)

      9999
    

    Plano de ExecuþÒo

    Plan hash value: 582132316


    | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |

    | 0 | SELECT STATEMENT | | 1 | 3 | 19 (0)| 00:00:01 |
    | 1 | SORT AGGREGATE | | 1 | 3 | | |

    |* 2 | INDEX RANGE SCAN| IDX_B_BTREE | 11007 | 33021 | 19 (0)| 00:00:01 |

    Predicate Information (identified by operation id):

    2 - access("B"='2')

    Note

    • 'PLAN_TABLE' is old version
    • dynamic sampling used for this statement

    EstatÝstica

         13  recursive calls
          0  db block gets
        101  consistent gets
        151  physical reads
          0  redo size
        336  bytes sent via SQL*Net to client
        392  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 count(b) from teste where b = '2' and b = '5';

    COUNT(B)

         0
    

    Plano de ExecuþÒo

    Plan hash value: 1118252671


    | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |

    | 0 | SELECT STATEMENT | | 1 | 3 | 0 (0)| |
    | 1 | SORT AGGREGATE | | 1 | 3 | | |
    |* 2 | FILTER | | | | | |

    |* 3 | INDEX RANGE SCAN| IDX_B_BTREE | 11007 | 33021 | 19 (0)| 00:00:01 |

    Predicate Information (identified by operation id):

    2 - filter(NULL IS NOT NULL)
    3 - access("B"='2')

    Note

    • 'PLAN_TABLE' is old version
    • dynamic sampling used for this statement

    EstatÝstica

          9  recursive calls
          0  db block gets
         81  consistent gets
          0  physical reads
          0  redo size
        334  bytes sent via SQL*Net to client
        392  bytes received via SQL*Net from client
          2  SQL*Net roundtrips to/from client
          0  sorts (memory)
          0  sorts (disk)
          1  rows processed
    

    SQL> drop index idx_b_btree;

    ═ndice eliminado.

    Agora, com o índice BITMAP

    SQL> create bitmap index idx_b_bitmap on teste (b);

    ═ndice criado.

    SQL> select count(b) from teste where b = '2';

    COUNT(B)

      9999
    

    Plano de ExecuþÒo

    Plan hash value: 4172640382


    | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |

    | 0 | SELECT STATEMENT | | 1 | 3 | 3 (0)| 00:00:01 |
    | 1 | SORT AGGREGATE | | 1 | 3 | | |
    | 2 | BITMAP CONVERSION TO ROWIDS| | 11007 | 33021 | 3 (0)| 00:00:01 |

    |* 3 | BITMAP INDEX SINGLE VALUE | IDX_B_BITMAP | | | | |

    Predicate Information (identified by operation id):

    3 - access("B"='2')

    Note

    • 'PLAN_TABLE' is old version
    • dynamic sampling used for this statement

    EstatÝstica

         44  recursive calls
          0  db block gets
         85  consistent gets
          4  physical reads
          0  redo size
        336  bytes sent via SQL*Net to client
        392  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 count(b) from teste where b = '2' and b = '5';

    COUNT(B)

         0
    

    Plano de ExecuþÒo

    Plan hash value: 934706267


    | Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |

    | 0 | SELECT STATEMENT | | 1 | 3 | 0 (0)| |
    | 1 | SORT AGGREGATE | | 1 | 3 | | |
    |* 2 | FILTER | | | | | |
    | 3 | BITMAP CONVERSION TO ROWIDS| | 11007 | 33021 | 3 (0)| 00:00:01 |

    |* 4 | BITMAP INDEX SINGLE VALUE | IDX_B_BITMAP | | | | |

    Predicate Information (identified by operation id):

    2 - filter(NULL IS NOT NULL)
    4 - access("B"='2')

    Note

    • 'PLAN_TABLE' is old version
    • dynamic sampling used for this statement

    EstatÝstica

          9  recursive calls
          0  db block gets
         77  consistent gets
          0  physical reads
          0  redo size
        334  bytes sent via SQL*Net to client
        392  bytes received via SQL*Net from client
          2  SQL*Net roundtrips to/from client
          0  sorts (memory)
          0  sorts (disk)
          1  rows processed
    

    O índice BITMAP teve um custo de 3 em relação aos 19 do índice B*tree, tornando-se mais eficiente para esse tipo de caso!

    Existe um porém também, a tabela é bem simples, usando CHAR como datatype e um volume de dados bem pequeno. Tem que ver se no seu ambiente vai ter a mesma eficiência.

    Nem sempre a boa prática é o que prevalece! Esse teste foi mais para matar a curiosidade.

    Abraços,

    Rodrigo Almeida
    [/code]