quinta-feira, 13 de fevereiro de 2014

Uso excessivo de distinct em banco de dados

Pra que usar distinct 

O comando distinct serve para eliminar linhas duplicadas em uma select. É um comando muito útil quando queremos remover linhas duplicadas quando todas as colunas resultam a mesma coisa.

O resultado final sera uma select com os dados já filtrados.

Eu particularmente não gosto, não recomendo e acho que o distinct é um comando utilizado para programadores preguiçosos. Nossa, não me matar por isso.

Veja, essa é minha opinião.

Em um sistema de padaria feito em casa com poucos registros é até válido. Mas vamos pensar em um ambiente compartilhado com um grande volume de informações e leituras em massa. O fato do banco retornar sua consulta em alguns segundos não quer dizer que esta consulta esta otimizada.

Dentro do banco de dados, muita coisa acontece somente para trazer esses registros filtrados.

Os problemas de performance ficam piores quando a base começa a crescer. Mas não deixe para otimizar suas querys somente após o problema começar, comece desde o primeiro registro pensando como essa informação sera resgatada posteriormente.

Mais da metade de problemas de lentidão no banco é devido as instruções SQL mal escritas.
O restante são ajustes, infra, sistema operacional e configurações diversas.

Como o banco de dados trata o distinct

Ao montar uma consulta, o banco de dados primeiramente procura um plano de execução que ja foi montado previamente.
Quando ele não encontra, ele ira fazer um hard parse. Isto é, ele vai verificar diversas coisas antes de retornar sua consulta. Exemplo : O usuário logado tem acesso ao banco, essa tabela existe, a select esta certa, quais são as colunas dessa tabela, as instruções estão na memória do servidor, os dados estão na memória, como vou buscar esses dados ?.
Feito isso, o banco ira retornar os dados.
Olha o tempo que perdemos com isso ?. 1 segundo... Agora imagine 1000 pessoas consultando ao mesmo tempo ?.

O distinct é mais um complicador.

Mas vamos dar um exemplo.

Tenho uma consulta que ira me trazer 5 milhões de registros, mas, eu preciso somente de 100 registros porque o resto é duplicação.

Ai vai lá o desenvolvedor e tem a brilhante ideia...DISTINCT nele.

O banco vai levar na memória 5 milhões de registros e utilizando CPU de forma desnecessária ele ira exibir somente os 100 registros que interessa.

Derrepentemente a base cresce de 5 milhões para 100 milhões de registros. Ai começa... o banco tá lento... o banco tá um lixo. Não... o banco não tá um lixo... A sua query é que é um lixo.

Ai chega o DBA e descobre o problema cobrando uma fortuna.

Quando for fazer uma query e precise filtrar registros duplicados, tenho duas técnicas que pode ser substituída pelo o Discinct 

1) Utilize GROUP BY

2) Faça todas as amarrações entre as tabelas utilizando preferencialmente os índices entre elas

Entenda primeiramente as tabelas, suas amarrações e principalmente, estude normalização de banco de dados.

Em breve irei postar um artigo sobre normalização de banco de dados.


Nenhum comentário:

Postar um comentário