Euler,
Eu escrevi:
No meu caso o que sempre fez e continua fazendo uma falta desgraçada no
Postgres é um otimizador decente (...) Bem que se podia aproveitar a
idéia aplicada no
Oracle ou no SQL Server e ter um cache de planos (...)
Isso já existe: chama-se comandos preparados (aka _prepared statements_).
Isso ??!
http://jdbc.postgresql.org/documentation/83/server-prepare.html
Não, não estou falando de algo tão simplório. Prepared statements têm
diversas desvantagens em relação ao que o Oracle e o SQL Server fazem:
* Prepared statements funcionam dentro da mesma conexão. Logo, consultas
idênticas feitas por instâncias diferentes da mesma aplicação ou
aplicações diferentes que façam as mesmas consultas continuarão tendo um
custo alto recompilando dúzias de vezes os mesmos comandos. Isso, é claro,
assumindo que eu me dê ao trabalho de mexer na minha aplicação para fazer
todas as consultas através da mesma conexão. O ganho disso seria bastante
questionável considerando que isso implica em serializar operações que
podem correr em paralelo.
* Da documentação:
"(...)
Server side prepared statements are planned only once by the server. This
avoids the cost of replanning the query every time, but also means that the
planner cannot take advantage of the particular parameter values used in a
particular execution of the query.
(...)"
Logo, Prepared statements usam o mesmo plano independente dos valores, o que
resulta em desastre. Isso é exatamente o *oposto* do que se espera de um
otimizador decente. O otimizador deveria ter uma lista de planos para a mesma
consulta e usar o mais adequado para cada uma.
É claro que você precisa manter a conexão mas nada que um aglomerador de
conexões (aka _pool_) não resolva.
Como expus acima, fazer isso, ainda por cima em larga escala, resulta em
desastre.
Como você mesmo disse, o tempo é relativamente pequeno em aplicações Web
e
OLTP; em OLAP, algumas consultas com dezenas de junções esse tempo é
significativo (aumenta 2^n mas é para isso que temos o GEQO) mas mesmo
assim
bem inferior ao de execução da consulta.
Dezenas de junções não são exclusividade de aplicações OLAP, muito pelo
contrário.
O fato de uma consulta cheia de junções exigir um enorme tempo de
planejamento de forma alguma implica em não valer a pena gastá-lo fazendo
isso. É exatamente nessas tabelas potencialmente grandes e cheias de índices
que uma escolha errada do otimizador resulta em planos catastróficos.
É fácil falar do otimizador mas é difícil mexer nele. ;)
Ora, ora, pelo menos nisso concordamos integralmente. A pergunta do tópico
foi quanto ao que se poderia melhorar em desempenho, só estou expondo a lista
para resolver os *meus* problemas. Afinal, custa-me acreditar que sou o único
interessado em desempenho por aqui.
Já tivemos essa discussão a um tempo atrás (...). Se eu me lembro bem,
nenhuma das
consultas apresentadas por você produzia um plano que não era ideal.
Depende do que chamarmos de "ideal". Para mim o ideal é medir as consultas em
milissegundos para poder comparar com Oracle e SQL Server, e não em minutos.
OK, de fato não tenho no momento exemplos usando a última versão do
Postgres, quando tiver passo para a lista. Fazer testes comparativos de
desempenho é algo que consome tempo que é dificílimo de conseguir
considerando nossas experiências anteriores.
Atenciosamente,
Mozart Hasse
_______________________________________________
pgbr-geral mailing list
[email protected]
https://listas.postgresql.org.br/cgi-bin/mailman/listinfo/pgbr-geral