quarta-feira, 6 de outubro de 2010

Catálogo do Postgres: uma imagem vale por mil palavras!

Compreender os metadados de um SGBD é a forma mais direta de saber como encontrar informações sobre o estado dos bancos de dados de um servidor. No caso do PostgreSQL, as várias tabelas e visões do sistema nem sempre são conhecidas pelo desenvolvedor, o que pode gerar problemas.

A imagem abaixo sintetiza o catálogo do Postgres em sua versão 8.3, apresentando uma visão geral das relações entre as tabelas de metadados. O diagrama não está compĺeto, por terem sido omitidos alguns dos atributos das relações e faltam visões de sistema como PG_TABLES e PG_LOCKS, mas me parece uma iniciativa pioneira para abrir estas informações para um público maior.

A imagem foi encontrada neste site peruano. Caso alguém conheça mais sobre a origem desta imagem e seu(s) autor(es) ou saiba de outra que englobe mais informação ou versões mais novas do Postgres, não deixe de me avisar!!!



segunda-feira, 4 de outubro de 2010

A Cláusula CASE

O uso de expressões condicionais dentro de SQL permite a geração de resultados mais claros sem a necessidade de se programar dentro do código das aplicações as condições a serem verificadas.

A cláusula CASE permite que os valores  retornados pelas consultas possam ser modificados caso sejam compatíveis com determinadas expressões de forma relativamente simples:

CASE WHEN condition THEN result
[WHEN ...]
[ELSE result]
END 


A cláusula CASE aceita uma condição consiste em uma expressão simples e retorna o valor que consta após a cláusula THEN, caso a condição seja satisfeita. Podem ser utilizados opcionalmente mais de um WHEN  no comando e a cláusula ELSE que é disparada quando nenhuma das condições do case seja satisfeita.

Abaixo, os comandos de criação de duas tabelas e a inserção de dados que serão utilizados para os exemplos de sintaxe:

CREATE TABLE VALORES (val INTEGER);
INSERT INTO VALORES VALUES (1);
INSERT INTO VALORES VALUES (2);

CREATE TABLE SIGNOS (val CHAR(1));
INSERT INTO SIGNOS VALUES ('A');
INSERT INTO SIGNOS VALUES ('T');
INSERT INTO SIGNOS VALUES ('G');

INSERT INTO SIGNOS VALUES ('X');

Sintaxe 1: Caso o valor numérico corresponda à condição, retorna uma string explicativa.


SELECT val,
CASE
    WHEN val=1 THEN 'Primeiro'
    WHEN val=2 THEN 'Segundo'
    ELSE 'Não Classificado'
END
FROM VALORES;


val |   case  
-----+----------
   1 | Primeiro
   2 | Segundo
(2 registros)


Sintaxe 2: Testa se o valor numérico é par ou ímpar e retorna uma string explicativa.



SELECT val,
CASE
    WHEN val%2=1 THEN 'Ímpar'
    WHEN val%2=0 THEN 'Par'
END
FROM VALORES;


val | case 
-----+-------
   1 | Ímpar
   2 | Par
(2 registros)

Sintaxe 3: O valor reTesta se o valor numérico é par ou ímpar e retorna uma string explicativa.


SELECT val,
CASE
    WHEN val='A' THEN 'Primeiro'
    WHEN val='T' THEN 'Segundo'
    WHEN val='G' THEN 'Terceiro'
    ELSE 'Não Classificado'
END
FROM SIGNOS;


 val |       case      
-----+------------------
 A   | Primeiro
 T   | Segundo
 G   | Terceiro
 X   | Não Classificado
(4 registros)


Nota: para condições mais complexas e que tomem muito tempo de processamento, pode ser criada uma função armazenada, que realiza as verificações de um case.