Quando falamos de performance em banco de dados, o primeiro termo que devemos associar é Indice. Indice é um ponteiro que o SGBD utiliza para localizar um ou mais de um registro de uma determinada tabela em um banco de dados.
Para melhorar nosso entendimento, imagine uma fita métrica onde a cada centímetro foi escrito uma letra aleatória, podendo a mesma ser utilizada mais de 1 vez ao longo da fita :
-----------------------------------------
| a f e a t f e r s a |
-----------------------------------------
1 2 3 4 5 6 7 8 9 10
Analogamente a uma tabela sem indice, ao ser executada uma consulta para trazer todas as letras "a" que existe na fita nós teriamos que ler toda a fita para descobrir que existem 3 letras "a" em toda sua extensão. Em banco de dados esse tipo de acesso a informação é denominado acesso FULL, ou seja, o SGBD faz uma leitura completa da tabela para encontrar as informações que são solicitadas.
Caso um índice fosse criado para essa fita, ele armazenaria o posicionamento de todas as letras que foram escritas ao longo dela. E quando uma consulta fosse executada para trazer todas as letras "a" que existe na fita, antes do acesso a fita, nós acessaríamos o índice que informaria a existência de uma letra "a" na posição 1, outra letra "a" na posição 4 e uma ultima letra "a" na posição 10, com isso nós não necessitaríamos ler toda a fita para descobrir quantas letras "a" existem na fita, o que tornaria o retorno da consulta muito mais rápido. Em banco de dados esse tipo de acesso a informação é denominado acesso BY INDEX.
Antes de sairmos criando índices em um banco de dados é necessário fazer algumas avaliações:
- Qual o foco principal da aplicação que acessa o banco de dados ?
- Qual a granularidade da informação onde queremos criar o índice ?
- Qual o índice ideal a ser criado ?
Todo índice é uma estrutura a mais no banco de dados que consome espaço e tempo de processamento. Espaço porque ele cria uma estrutura a parte da tabela com chaves e ponteiros apontando para os dados da tabela e tempo de processamento porque o índice sofre alteração quando sua tabela de referência sofre alteração.
Analisar o foco principal da aplicação é importante porque os índices melhoram a performance das consultas a uma base de dados, mas degrada a performance das inserções, deleções e atualizações. Toda inserção, deleção e atualização de registros em uma tabela implica em atualização dos indices associados a ela que dependendo da quantidade de índices, do tamanho e da reorganização deles podem consumir muito tempo de processamento. Se o foco principal da aplicação é gerar relatórios índices podem ser criados para tornar a performance dos relatórios melhores, porém se o foco da aplicação é o cadastro de informações é importante avaliar a real necessidade de se criar índices para ela.
A granularidade de um campo diz respeito a variação de informações que ele representa. Vamos imaginar uma tabela de clientes onde existem apenas 3 campos RG, Primeiro Nome e Sexo. O campo Sexo só pode ter 2 opções masculino e feminino. Esse campo é considerado com granularidade baixa pois a variação de informações que ele representa são apenas duas. Campos com granularidade baixa não são indicados para criação de índices, pois o custo de acesso ao índice mais o custo de acesso a grande quantidade de dados retornados não compensa em relação a um acesso FULL a tabela. Imagine uma tabela com 50% de clientes do sexo masculino e 50% do sexo feminino, se fossemos consultar todos os clientes com sexo masculino a quantidade de registros retornados é metade da tabela. Caso a tabela tivesse 90% de clientes do sexo masculino e 10% do sexo feminino essa consulta retornaria praticamente todos os registros da tabela e ainda perderíamos o tempo de acesso ao índice. Já o campo RG possui uma variação muito grande de valores, praticamente um valor exclusivo para cada registro. Esse tipo de campo possui uma granularidade muito alta e é o tipo de campo mais indicado para criação de um índice. O desempenho de qualquer consulta que utiliza índices em campos de granularidade alta é excelente, pois a quantidade de acesso a disco é muito pequena e quanto menos acesso a disco uma consulta fizer mais rápido é o tempo de resposta dela. O campo Primeiro Nome é considerado com granularidade média, pois os valores podem se repetir muitas vezes mas a variação de valores também é muito grande. Esse tipo de campo também é indicado para criação de índices, apesar de não ser perfeito ele é muito bom.
O conhecimento do negócio é um fator determinante para tomadas de decisões em relação a criação de índices ou não. Apesar de campos com granularidade baixa não serem indicados para criação de índices existem processos onde eles funcionam muito bem. Como exemplo, podemos citar um processo que recebe uma carga de registros todos os dias e esses registros são processados logo em seguida. No registro existe um campo de status que informa se aquele registro já foi processado ou não, sendo "N" igual a "Não processado" e "S" igual a "Processado". Apesar da granularidade baixa, pois o campo recebe somente 2 valores, se o processamento é feito apenas nos registros com valores igual a "N", a tendencia é que a quantidade de registros com "N" seja muito menor que a quantidade de registros com "S" e a criação de um índice para esse campo pode tornar o processo muito mais rápido do que o acesso FULL a tabela. Porém somente a criação do índice e a execução de uma consulta que utiliza o campo do índice não implica em utilização do índice pela banco. Quem determina a utilização ou não do índice é o SGBD de acordo com o melhor plano de execução montado para aquela consulta e normalmente índices com granularidade baixa são desconsiderados pelo SGBD, nesses casos é necessário a utilização de um HINT para forçar a utilização do índice para a consulta. Em outro post falaremos sobre HINTS.
Espero ter ajudado um pouco e em breve retornarei com outras dicas!
Abraços