Desmistificando o SELECT no SQL Server: Processamento Lógico vs Processamento Físico

Quando eu começei a ler sobre o processamento lógico das queries, eu “boiei” muito.
Sabia que era um assunto bem legal, mas nao entendia realmente o que era.

Depois de algum tempo de leitura e pesquisa, acho que finalmente entendi, e, por experiencia própria acredito que seja mais do que importante entender bem esse assunto.

Para o SQL Server processar aquele comando SQL, ele tem algo como “regras”.
Ele vai validar o comando pra ver se está de acordo com a sintaxe do SQL, checar se as tabelas existem, etc…

Todo esse procedimento segue uma lógica. Essa lógica guia o modo como a engine do SQL Server irá interpretar o comando.
Por exemplo, veja a seguinte query: (Os scrips para criação dessas tabelas está aqui)

SELECT
     C.cidade
    ,COUNT(P.pedidoID)
FROM
    dbo.Cliente C
    LEFT JOIN
    dbo.Pedido P
	   ON P.clienteID = C.clienteID
GROUP BY
    C.cidade

É uma query muito simples. O que ela faz é trazer a quantidade de pedidos por cidade.
Vamos viajar um pouco. Imagine que você fosse o SQL Server e estivesse responsável por processar a query.
De cara, você começa a processar a query a partir do início, isto é, da cláusula SELECT:

Ai você dá de cara com esse primeiro trecho do comando:

SELECT
	c.cidade

Ai você se pergunta, “C.cidade” ? Qual tabela o alias “C” representa ?
Opa, você percebeu que nao podemos começar o processamento pelo SELECT, porque primeiro precisamos saber quais as tabelas e alias o desenvolvedor informou na query.

E onde estão essas informações ? Na cláusula FROM!!

Agora veja esta outra query:

SELECT DISTINCT
     UPPER(C.cidade) AS NomeCidade
FROM
    dbo.Cliente C
ORDER BY
    NomeCidade

Essa query pode ter várias interpretações diferentes, isto é, várias “lógicas de processamento” diferentes.Cada lógica escolhida no seu processamento vai produzir um resultado diferente. Quer ver ? Então vamos lá.

Vamos supor que a lógica de processamento que voce escolheria fosse a seguinte: (de novo, imaginando que você  é o SQL Server)

1º – FROM
2º – ORDER BY
3º – SELECT
Bem vamos lá, o FROM seria moleza. Você teria apenas que ler os dados da tabela Cliente e atribuir o alias “C” a ela.

Logo em seguida viria o ORDER BY. Opa, temos um problema, a tabela Cliente nao tem uma coluna ‘NomeCidade‘. Essa coluna é um alias definido no SELECT, e como você ainda não processou o SELECT, não sabe da existencia desse alias. Nesse caso, representando o SQL Server, o que fazer? Simples: Informaria um erro ao usuário:

“Erro 0000: A coluna NomeCidade nao foi encontrada”

Assim, nessa ordem de processamento o resultado seria um erro. Agora, vamos imaginar que a ordem escolhida fosse essa:

1º – FROM
2º – SELECT
3º – ORDER BY

De novo, a primeira fase é processar o FROM: apenas ler tabela Clientes e atribuir o alias “C” a ela.
Agora, vem a fase do SELECT. Nessa parte ele menciona “C.cidade”. Como já processamos o FROM, sabemos que o “C” representa a tabela “Cliente”. Legal, com isso nós vimos que o desenvolvedor está querendo referenciar uma coluna chamada “cidade” da tabela Cliente. O próximo passo seria verificar se a coluna realmente foi retornada pelo FROM, mas não se preocupe com isso agora.

Continuando o processamento do SELECT, aplicariamos a funcao UPPER na coluna “C.cidade”. Por último, nós iríamos associar o alias “NomeCidade” ao resultado desta função. Até aqui tudo bem.

Enfim, processaríamos o ORDER BY. Como já processamos o SELECT, nó sabemos que o nome “NomeCidade” é uma alias pro resultado da expressão “UPPER(C.Cidade)”

Agora é so ordenar os dados de acordo com o resultado dessa função, e pronto!

Tá vendo ? Olhe só que interessante.
Na primeira tentativa, o nosso processamento resultou em um erro.
Na segunda, apenas por trocar o ORDER BY de lugar com o SELECT, ja produziu um resultado sem erros.

Isso não se resume a resultados com erros ou não. Dependendo de como você acha que sua query ai ser executada, você pode imaginar que vai vir uma coisa, quando na verdade vem outra…

É por isso que é bastante importante entender como o SQL Server irá avaliar seu comando SQL. Entender como é a lógica usada por ele, o que chamamos de processamento lógico da query (Logical Query Processing). Entendo o processamento lógico da query é a chave para escrever consultas mais eficientes e robustas.

E o processamento físico ?

O processamento lógico na verdade é só um conceito… A microsoft apenas implementou as regras deste conceito. O modo como o SQL Server vai acessar os dados, filtrar, etc… “são outros 500 …”.

Você so precisa saber que o resultado produzido pelo processamento físico deve ser exatamente o mesmo produzido no processamento lógico. Assim, quando formos analisarmos o plano de execução (que indica como o SQL irá executar a query) iremos ver passos em uma ordem muito diferente do processamento lógico, mas pode ter certeza que o resultado produzido, será o mesmo do processamento lógico.

Bom, espero que esse post nao tenha ficado confuso. Esse lance de processamento físico e lógico vai ser esclarecido conforme formos vendo cada fase do processamento lógico.

Qualquer dúvida, sugestão, crítica, etc., por favor, coloque nos comentários que estarei respondendo.
Até a próxima.

[]’s
Rodrigo Ribeiro Gomes
MTA|MCTS

Advertisements

2 thoughts on “Desmistificando o SELECT no SQL Server: Processamento Lógico vs Processamento Físico

  1. Achei uma coisa curiosa, o a cláusa Order By é a ultima executada no processamento lógico, mas mesmo assim o comando, abaixo funcionou:

    SELECT DISTINCT
    UPPER(C.cidade) AS NomeCidade
    FROM
    dbo.Cliente C
    ORDER BY
    NomeCidade

    Já o seguinte comando com a cláusula Where, não funcionou:
    SELECT DISTINCT
    UPPER(C.cidade) AS NomeCidade
    FROM
    dbo.Cliente C
    where
    NomeCidade = ‘BRASILIA’
    fala que o cluna chamada NomeCidade não foi encontrada.
    Eu entendo qual o motivo de não funcionar no Where, mas não entendo o por quê funciona na cláusula Order By.
    Abs,
    Andrey Filipe.

    • Boa noite Andrey.

      O motivo de funcionar é justamente o que você falou: o ORDER BY é o último a ser processado. Isto significa que ele já sabe da existência do alias “NomeCidade”, e então consegue ordenar usando este nome.

      Ao contrário do Where, que é processado antes da fase do SELECT (onde o alias “NomeCidade” é definido). Por isso o WHERE dá erro.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s