Estão disponíveis os operadores de comparação usuais, confome descrito na Tabela 9.1.
Tabela 9.1. Operadores de comparação
| Operador | Descrição |
|---|---|
datatype < datatype
→ boolean
| Menor que |
datatype > datatype
→ boolean
| Maior que |
datatype <= datatype
→ boolean
| Menor que ou igual a |
datatype >= datatype
→ boolean
| Maior que ou igual a |
datatype = datatype
→ boolean
| Igual |
datatype <> datatype
→ boolean
| Não igual |
datatype != datatype
→ boolean
| Não igual |
<> é a notação do padrão SQL para
“não igual”. != é um alias,
convertido para <> em um estágio muito
inicial da análise. Assim, não é possível implementar operadores
!= e <> que façam
coisas diferentes.
Estes operadores de comparação estão disponíveis para todos os tipos de dados internos que possuem uma ordenação natural, incluindo os tipos de dados numéricos, de cadeia de caracteres e de data e hora. Além disso, matrizes, tipos de dados compostos e intervalos podem ser comparados se os tipos de dados de seus componentes forem comparáveis.
Geralmente, também é possível comparar valores de tipos de dados
relacionados; por exemplo, integer >
bigint funciona.
Alguns casos assim são implementados diretamente por operadores
de comparação de “tipo-cruzado”, mas se nenhum operador
estiver disponível, o analisador força o tipo de dados menos geral
para o tipo de dados mais geral e aplica a comparação deste último
operador.
Como mostrado acima, todos os operadores de comparação são operadores
binários que retornam valores do tipo de dados boolean.
Portanto, expressões como 1 < 2 < 3 não são
válidas (porque não existe o operador < para
comparar o valor booleano com 3).
Para realizar testes de intervalo devem ser usados os predicados
BETWEEN mostrados abaixo.
Também existem alguns predicados de comparação, como descrito na Tabela 9.2. Eles se comportam como operadores, mas possuem uma sintaxe especial exigida pelo padrão SQL.
Tabela 9.2. Predicados de comparação
Predicado Descrição Exemplo(s) |
|---|
Entre (incluindo os pontos das extremidades do intervalo).
|
Não entre (a negação do
|
Entre, após classificar os dois valores das extremidades.
|
Não entre, após classificar os dois valores das extremidades.
|
Não igual, tratando nulo como valor comparável.
|
Igual, tratando nulo como valor comparável.
|
Testa se o valor é nulo.
|
Testa se o valor não é nulo.
|
Testa se o valor é nulo (sintaxe fora do padrão). |
Testa se o valor não é nulo (sintaxe fora do padrão). |
Testa se a expressão booleana resulta em verdade.
|
Testa se a expressão booleana resulta em falso ou desconhecido.
|
Testa se a expressão booleana resulta em falso.
|
Testa se a expressão booleana resulta em verdade ou desconhecido.
|
Testa se a expressão booleana resulta em desconhecido.
|
Testa se a expressão booleana resulta em verdade ou falso.
|
O predicado BETWEEN simplifica os testes de intervalo:
aBETWEENxANDy
equivale a
a>=xANDa<=y
Note que BETWEEN trata os valores das extremidades
como incluídos no intervalo.
BETWEEN SYMMETRIC é como BETWEEN,
exceto não haver a exigência de que o argumento à esquerda do
AND seja menor ou igual ao argumento à direita.
Se não for menor, estes dois argumentos são trocados automaticamente,
de modo que está sempre implícito um intervalo não vazio.
As várias formas alternativas de BETWEEN são
implementadas em termos de operadores de comparação comuns,
portanto funcionam para qualquer tipo de dados que possa ser comparado.
O uso do AND na sintaxe do
BETWEEN cria ambiguidade com o uso do
AND como operador lógico.
Para resolver este problema, é permitido apenas um conjunto limitado
de tipos de expressão como segundo argumento da cláusula
BETWEEN.
Se for necessário escrever uma subexpressão mais complexa em
BETWEEN, devem ser colocados parênteses ao
redor da subexpressão.
Operadores de comparação comuns produzem nulo (significando
“desconhecido”), e não verdade ou falso, quando
uma das entradas é nula.
Por exemplo, 7 = NULL resulta em nulo, assim como
7 <> NULL. Quando esse comportamento não
for adequado, devem ser usados os predicados
IS [ NOT ] DISTINCT FROM:
aIS DISTINCT FROMbaIS NOT DISTINCT FROMb
Para entradas não nulas, IS DISTINCT FROM
é idêntico ao operador <>.
Entretanto, se as duas entradas forem nulas retorna falso e,
se apenas uma entrada for nula, retorna verdade.
De forma semelhante, IS NOT DISTINCT FROM é
idêntico a = para entradas não nulas,
mas retorna verdade quando as duas entradas são nulas, e falso
quando apenas uma entrada é nula.
Portanto, estes predicados atuam de fato como se nulo fosse um
valor de dados normal, em vez de “desconhecido”.
Para verificar se o valor é ou não nulo, devem ser usados os predicados
expressãoIS NULLexpressãoIS NOT NULL
ou os predicados equivalentes, mas fora do padrão SQL:
expressãoISNULLexpressãoNOTNULL
Não escreva
,
porque expressão = NULLNULL “não é igual” a
NULL. (O valor nulo representa o valor
desconhecido, e não é possível saber se dois valores desconhecidos
são iguais.)
Algumas aplicações podem esperar que
retorne verdade se a expressão = NULLexpressão resulta no
valor nulo.
É altamente recomendável que estas aplicações sejam modificados para
ficarem em conformidade com o padrão SQL.
Entretanto, se isto não puder ser feito, está disponível a variável
de configuração transform_null_equals.
Se esta variável estiver ativa, o
PostgreSQL irá converter as cláusulas
x = NULL para x IS NULL.
Se a expressão for um valor de linha,
então IS NULL será verdade quando a própria
expressão de linha for nula, ou quando todos os campos da linha
forem nulos, enquanto IS NOT NULL será verdade
quando a própria expressão de linha não é nula e todos os campos
da linha não são nulos. Devido a este comportamento,
IS NULL e IS NOT NULL nem
sempre retornam resultados inversos para expressões com valor de
linha; em particular, uma expressão com valor de linha contendo
campos nulos e não nulos retorna falso para os dois testes.
Por exemplo:
SELECT ROW(1,2.5,'isto é um teste') = ROW(1, 3, 'não e o mesmo'); SELECT ROW(tabela.*) IS NULL FROM tabela; -- detecta linhas inteiramente nulas SELECT ROW(tabela.*) IS NOT NULL FROM tabela; -- detecta todas as linhas não nulas SELECT NOT(ROW(tabela.*) IS NOT NULL) FROM TABELA; -- detecta pelo menos um valor nulo nas linhas
Em alguns casos, pode ser preferível escrever
linha
IS DISTINCT FROM NULL
ou linha
IS NOT DISTINCT FROM NULL,
que apenas verifica se o valor global da linha é nulo sem
nenhum teste adicional nos campos da linha.
Os valores booleanos também podem ser testados usando os predicados:
expressão_booleanaIS TRUEexpressão_booleanaIS NOT TRUEexpressão_booleanaIS FALSEexpressão_booleanaIS NOT FALSEexpressão_booleanaIS UNKNOWNexpressão_booleanaIS NOT UNKNOWN
Estes sempre retornam verdade ou falso, nunca o valor nulo, mesmo
quando o operando for nulo. Uma entrada nula é tratada como o valor
lógico “desconhecido”.
Note que IS UNKNOWN e
IS NOT UNKNOWN são de fato idênticos a
IS NULL e IS NOT NULL,
respectivamente, exceto pela expressão de entrada que deve ser do
tipo de dados booleano.
Também estão disponíveis algumas funções relacionadas à comparação, como descrito na Tabela 9.3.
Tabela 9.3. Funções de comparação