[firebase-br] NOT EXISTS

Gladiston Santana gladiston em vidy.com.br
Ter Jul 22 18:25:16 -03 2014


Como eu disse, ou você perde tempo na précompilação ou perderá depois.
O FB pode simplesmente ter invertido a sua querie ou usado um indice
invertido, ou ainda um table scan,... enfim, o fato é que algo teve de ser
processado para determinar o que fazer e um simples NOT pode ter
acrescentando uma complexidade ao processo que poderia ter resultado num
tempo maior se não fosse a intervenção do pré-compilador.
Não se trata de NOT EXIST, NOT IN,... trata-se do peso do NOT em equações
com listas.
Pode ser escovação de bits da minha parte, mas em todos os trabalhos de
consultoria que faço onde a queixa é performance, troco os NOT EXIST por
EXIST ou LEFT JOIN ou mudo a lógica a fim de facilitar para o compilador e
tenho tido muitos resultados positivos, é obvio que em alguns casos não dá,
mas a maioria dá. Estou falando apenas de subqueries.
Minha premissa é simplificar ao compilador, mesmo que no resultado no
final, o ganho tenha sido desprezível.
Eu não confundiria nunca NOT EXIST com NOT IN, este ultimo quando usado com
subquery o parser poderia dizer 'tá errado sua anta...' que eu ficaria
aliviado :)

ate+

Em 22 de julho de 2014 17:38, Carlos H. Cantu <listas em warmboot.com.br>
escreveu:

> GS> Para um not atingir um alvo todos os elementos terão de ser
> GS> resgatados, para um exist, o primeiro elemento encontrado é o
> GS> suficiente para alvo estar completo.
> GS> Não importa o plano escolhido, na mesma perspectiva a negação
> GS> sempre será pior, seja na hora do resgate ou na pré-compilação onde
> determinará o plano.
> GS>  Estou admirado em você não se lembrar disso.
>
> Vamos para a prática:
>
> /* Todos os produtos que tiveram notas emitidas a partir de 1.1.2010 */
> select P.CODPROD
> from PRODUTOS P
> where exists(select *
>                  from NOTAS N
>                  join PRODNOTA PN on PN.ID_NUM = N.ID_NUM and PN.CODPROD =
> P.CODPROD
>                  where N.EMISSAO > '1.1.2010')
>
> e
>
> /* Todos os produtos que NÃO tiveram notas emitidas a partir de 1.1.2010 */
> select P.CODPROD
> from PRODUTOS P
> where NOT exists(select *
>                  from NOTAS N
>                  join PRODNOTA PN on PN.ID_NUM = N.ID_NUM and PN.CODPROD =
> P.CODPROD
>                  where N.EMISSAO > '1.1.2010')
>
>
> Ambos usaram o mesmo PLAN, tiveram a mesma performance e o mesmo número de
> leituras
> (indexadas e não indexadas). Ou seja, o NOT aqui não prejudicou em
> nada a performance.
>
> Como eu disse, não confunda NOT IN com NOT EXISTS, pois são coisas
> diferentes dependendo de como forem usados.
>
> []s
> Carlos H. Cantu
> www.FireBase.com.br - www.firebirdnews.org
> www.warmboot.com.br - blog.firebase.com.br
>
> GS> Para um not atingir um alvo todos os elementos terão de ser
> GS> resgatados, para um exist, o primeiro elemento encontrado é o
> GS> suficiente para alvo estar completo.
>
> GS> Não importa o plano escolhido, na mesma perspectiva a negação
> GS> sempre será pior, seja na hora do resgate ou na pré-compilação onde
> determinará o plano.
> GS>  Estou admirado em você não se lembrar disso.
> GS> Não usei 'select first 1', usei 'select 1' porque simplesmente
> GS> não preciso de nenhum campo, estou apenas testando a existência -
> GS> em alguns RDBMS isso economiza bytes ao parser, provavelmente no FB
> também.
> GS>
> GS> Um cordial abraço,
>



Mais detalhes sobre a lista de discussão lista