Espero esclarecer aqui minha posição.
Essa NULL = NULL
avaliação FALSE
está errada. Hacker e Mister responderam corretamente NULL
. Aqui está o porquê. Dewayne Christensen escreveu para mim, em um comentário para Scott Ivey :
Como é dezembro, vamos usar um exemplo sazonal. Eu tenho dois presentes embaixo da árvore. Agora, você me diz se eu tenho duas da mesma coisa ou não.
Eles podem ser diferentes ou iguais, você não sabe até que um abra os dois presentes. Quem sabe? Você convidou duas pessoas que não se conhecem e ambos têm feito para você o mesmo dom - raro, mas não impossível § .
Portanto, a pergunta: esses dois DESCONHECIDOS apresentam o mesmo (igual, =)? A resposta correta é: DESCONHECIDO (ie NULL
).
Este exemplo teve como objetivo demonstrar que ".. ( false
ou null
, dependendo do seu sistema) .." é uma resposta correta - não é, apenas NULL
é correta em 3VL (ou é aceitável que você aceite um sistema que fornece respostas erradas? )
Uma resposta correta para esta pergunta deve enfatizar esses dois pontos:
- a lógica de três valores (3VL) é contra-intuitiva (consulte inúmeras outras perguntas sobre esse assunto no Stackoverflow e em outro fórum para garantir);
- Os DBMSs baseados em SQL geralmente não respeitam até 3VL, mas às vezes dão respostas erradas (como afirma o pôster original, o SQL Server nesse caso).
Por isso, reitero: o SQL não ajuda em nada a interpretar a propriedade reflexiva da igualdade, que afirma que:
for any x, x = x
§§ (em inglês simples: seja qual for o universo do discurso, uma "coisa" é sempre igual a si mesma ).
.. num 3VL ( TRUE
, FALSE
, NULL
). A expectativa das pessoas estaria de acordo com 2VL ( TRUE
, FALSE
que mesmo em SQL é válida para todos os outros valores), ou seja, x = x
sempre avaliar a TRUE
, para qualquer valor possível de x - sem exceções.
Observe também que os NULLs são " não valores " válidos (como seus apologistas pretendem que sejam) que podem ser atribuídos como valores de atributo (??) como parte das variáveis de relação. Portanto, eles são valores aceitáveis de todos os tipos (domínio), não apenas do tipo de expressões lógicas.
E esse foi o meu argumento : NULL
como valor, é uma "besta estranha". Sem eufemismo, prefiro dizer: bobagem .
Eu acho que essa formulação é muito mais clara e menos discutível - desculpe pela minha baixa proficiência em inglês.
Este é apenas um dos problemas dos NULLs. Melhor evitá-los completamente, quando possível.
§ estamos preocupados com os valores aqui; portanto, o fato de os dois presentes serem sempre dois objetos físicos diferentes não é uma objeção válida; se você não está convencido, desculpe, não é este o lugar para explicar a diferença entre semântica de valor e de "objeto" (a Álgebra Relacional tem semântica de valor desde o início - consulte o princípio da informação do Codd; acho que alguns implementadores do SQL DBMS não nem se importa com uma semântica comum).
§§ que eu saiba, esse é um axioma aceito (de uma forma ou de outra, mas sempre interpretado em uma 2VL) desde a antiguidade e exatamente por ser tão intuitivo. 3VLs (é uma família de lógicas na realidade) é um desenvolvimento muito mais recente (mas não tenho certeza de quando foi desenvolvido).
Nota lateral: se alguém introduzir os tipos Bottom , Unit e Option como tentativas de justificar SQL NULLs, ficarei convencido apenas após um exame bastante detalhado que mostrará como as implementações SQL com NULLs têm um sistema de tipo de som e esclarecerá, finalmente, o que realmente são NULLs (esses "valores-não-valores-iguais").
A seguir, citarei alguns autores. Qualquer erro ou omissão é provavelmente meu e não dos autores originais.
Joe Celko em SQL NULLs
Eu vejo Joe Celko frequentemente citado neste fórum. Aparentemente, ele é um autor muito respeitado aqui. Então, eu disse a mim mesmo: "o que ele escreveu sobre SQL NULLs? Como ele explica vários problemas com NULLs?". Um amigo meu tem uma versão eletrônica do SQL for smarties de Joe Celko: programação SQL avançada, 3ª edição . Vamos ver.
Primeiro, o sumário. O que mais me impressiona é o número de vezes que NULL é mencionado e nos mais variados contextos:
3.4 Aritmética e NULLs 109
3.5 Convertendo valores de e para NULL 110
3.5.1 Função NULLIF () 110
6 NULLs: dados ausentes no SQL 185
6.4 Comparando NULLs 190
6.5 NULLs e lógica 190
6.5.1 NULLS e Predicados do Subquery 191
6.5.2 Padrão Soluções SQL 193
6.6 Matemática e NULLs 193
6,7 Funções e NULLs 193
6,8 NULLs e idiomas do host 194
6,9 Recomendações de design para NULLs 195
6.9.1 Evitar NULLs dos programas host 197
6.10 Uma observação sobre vários valores NULL 198
10.1 Predicado IS NULL 241
10.1. 1 Fontes de NULLs 242
...
e assim por diante. Soa "um caso especial desagradável" para mim.
Vou abordar alguns desses casos com trechos deste livro, tentando me limitar ao essencial, por razões de direitos autorais. Acho que essas citações se enquadram na doutrina do "uso justo" e podem até estimular a compra do livro - por isso espero que ninguém reclame (caso contrário, precisarei excluir a maior parte, se não todas). Além disso, evitarei relatar trechos de código pelo mesmo motivo. Me desculpe por isso. Compre o livro para ler sobre o raciocínio com dados.
Números de página entre parênteses a seguir.
Restrição NÃO NULL (11)
A restrição de coluna mais importante é o NOT NULL, que proíbe o uso de NULLs em uma coluna. Use essa restrição rotineiramente e remova-a apenas quando tiver um bom motivo. Isso ajudará a evitar as complicações dos valores NULL quando você fizer consultas nos dados.
Não é um valor ; é um marcador que ocupa um lugar onde um valor pode ir.
Mais uma vez, esse absurdo de "valor, mas não exatamente um valor". O resto parece bastante sensato para mim.
(12)
Em resumo, os NULLs causam muitos recursos irregulares no SQL, os quais discutiremos mais adiante. Sua melhor aposta é apenas para memorizar as situações e as regras para NULLs quando você não puder evitá-las.
A propósito de SQL, NULLs e infinito:
(104) CAPÍTULO 3: DADOS NUMÉRICOS EM SQL
O SQL não aceitou o modelo IEEE para matemática por vários motivos.
...
Se as regras IEEE para matemática fossem permitidas no SQL, precisaríamos de regras de conversão de tipo para infinito e uma maneira de representar um valor numérico exato infinito após a conversão. As pessoas têm problemas suficientes com NULLs, então não vamos lá.
Implementações de SQL indecisas sobre o que NULL realmente significa em contextos específicos:
3.6.2 Funções exponenciais (116)
O problema é que os logaritmos são indefinidos quando (x <= 0). Algumas implementações SQL retornam uma mensagem de erro, outras retornam um NULL e DB2 / 400; a versão 3, liberação 1, retornou * NEGINF (abreviação de "infinito negativo") como resultado.
Joe Celko citando David McGoveran e CJ Date:
6 NULLs: dados ausentes no SQL (185)
No livro A Guide to Sybase e SQL Server , David McGoveran e CJ Date disseram: “A opinião deste escritor é que os NULLs, pelo menos como atualmente definidos e implementados no SQL, são muito mais problemáticos do que valem a pena e devem ser evitados; eles exibem um comportamento muito estranho e inconsistente e podem ser uma rica fonte de erro e confusão. (Observe que esses comentários e críticas se aplicam a qualquer sistema que suporte NULLs no estilo SQL, não apenas ao SQL Server especificamente.) ”
Nulos como um vício em drogas :
(186/187)
No restante deste livro, pedirei que você não os use , o que pode parecer contraditório, mas não é. Pense em um NULL como uma droga; use-o corretamente e funcione para você, mas abuse e pode estragar tudo. Sua melhor política é evitar NULLs quando possível e usá-los adequadamente quando necessário.
Minha objeção exclusiva aqui é "usá-los adequadamente", que interage mal com comportamentos de implementação específicos.
6.5.1 NULLS em predicados de subconsulta (191/192)
As pessoas esquecem que uma subconsulta geralmente oculta uma comparação com um NULL. Considere estas duas tabelas:
...
O resultado estará vazio. Isso é contra - intuitivo , mas correto.
(separador)
6.5.2 Soluções SQL padrão (193)
O SQL-92 resolveu alguns dos problemas de 3VL (lógica de três valores) adicionando um novo predicado do formulário:
<condição de pesquisa> É [NÃO] VERDADEIRO | FALSO DESCONHECIDO
Mas UNKNOWN é uma fonte de problemas em si, de modo que CJ Date, em seu livro citado abaixo, é recomendado no capítulo 4.5. Evitando nulos no SQL :
- Não use a palavra-chave DESCONHECIDA em nenhum contexto.
Leia "ASIDE" em DESCONHECIDO, também linkado abaixo.
6.8 NULLs e idiomas do host (194)
No entanto, você deve saber como os NULLs são tratados quando precisam ser passados para um programa host. Nenhum idioma padrão do host para o qual uma incorporação é definida oferece suporte a NULLs, o que é outro bom motivo para evitar usá-los no esquema do banco de dados.
(separador)
6.9 Conselho de design para NULLs (195)
É uma boa ideia declarar todas as suas tabelas base com restrições NOT NULL em todas as colunas sempre que possível. NULLs confundem pessoas que não conhecem SQL, e NULLs são caros.
Objeção: NULLs confunde até pessoas que conhecem bem o SQL, veja abaixo.
(195)
NULLs devem ser evitados em CHAVES ESTRANGEIRAS. O SQL permite esse relacionamento de "benefício da dúvida", mas pode causar perda de informações nas consultas que envolvem junções. Por exemplo, dado um código de número de peça no Inventário que é referenciado como uma CHAVE ESTRANGEIRA por uma tabela Pedidos, você terá problemas para obter uma lista das peças que possuem um NULL. Este é um relacionamento obrigatório; você não pode solicitar uma peça que não existe.
(separador)
6.9.1 Evitando NULLs dos programas host (197)
Você pode evitar colocar NULLs no banco de dados nos Programas Host com alguma disciplina de programação.
...
- Determine o impacto de dados ausentes na programação e nos relatórios: as
colunas numéricas com NULLs são um problema, porque as consultas usando funções agregadas podem fornecer resultados enganosos.
(separador)
(227)
O SUM () de um conjunto vazio é sempre NULL. Um dos erros de programação mais comuns cometidos ao usar esse truque é escrever uma consulta que possa retornar mais de uma linha. Se você não pensou sobre isso, pode ter escrito o último exemplo como: ...
(separador)
10.1.1 Fontes de NULLs (242)
É importante lembrar onde os NULLs podem ocorrer. Eles são mais do que apenas um valor possível em uma coluna . Funções agregadas em conjuntos vazios, OUTER JOINs, expressões aritméticas com NULLs e operadores OLAP retornam NULLs. Essas construções costumam aparecer como colunas em VIEWs.
(separador)
(301)
Outro problema com NULLs é encontrado quando você tenta converter predicados IN em predicados EXISTS.
(separador)
16.3 O predicado ALL e as funções Extrema (313)
É contra-intuitivo a princípio que esses dois predicados não sejam os mesmos no SQL:
...
Mas você precisa se lembrar das regras para as funções extremas - elas eliminam todos os NULLs antes de retornar os valores maiores ou menores. O predicado ALL não descarta NULLs, para que você possa obtê-los nos resultados.
(separador)
(315)
No entanto, a definição no padrão é redigida em negativo, para que os NULLs obtenham o benefício da dúvida. ...
Como você pode ver, é uma boa idéia evitar NULLs em restrições UNIQUE.
Discutindo GROUP BY:
NULLs são tratados como se fossem todos iguais e formam seu próprio grupo. Cada grupo é então reduzido a uma única linha em uma nova tabela de resultados que substitui a antiga.
Isso significa que para a cláusula GROUP BY NULL = NULL não é avaliado como NULL, como em 3VL, mas é avaliado como TRUE.
O padrão SQL é confuso:
ORDER BY e NULLs (329)
Se um valor de chave de classificação que é NULL é considerado maior ou menor que um valor não-NULL é definido pela implementação, mas ...
... Existem produtos SQL que fazem isso de qualquer maneira.
Em março de 1999, Chris Farrar levantou uma pergunta de um de seus desenvolvedores que o levou a examinar uma parte do SQL Standard que eu pensava entender . Chris encontrou algumas diferenças entre o entendimento geral e a redação real da especificação .
E assim por diante. Eu acho que é o suficiente por Celko.
Data CJ em SQL NULLs
A data CJ é mais radical quanto aos NULLs: evite NULLs no SQL, ponto final. De fato, o capítulo 4 de sua SQL e a teoria relacional: Como escrever um código SQL preciso é intitulado "SEM DUPLICADOS, SEM NULOS", com os subcapítulos
"4.4 O que há de errado com os nulos?" e "4.5 Evitando nulos no SQL" (siga o link: graças ao Google Livros, você pode ler algumas páginas on-line).
Fabian Pascal em SQL NULLs
De suas questões práticas no gerenciamento de banco de dados - uma referência para o profissional que pensa (sem trechos on-line, desculpe):
10.3 Implicações práticas
10.3.1 NULL SQL
... O SQL sofre dos problemas inerentes à 3VL, bem como de muitas peculiaridades, complicações, contra-intuitividade e erros definitivos [10, 11]; entre eles estão os seguintes:
- Funções agregadas (por exemplo, SUM (), AVG ()) ignoram NULLs (exceto COUNT ()).
- Uma expressão escalar em uma tabela sem linhas é avaliada incorretamente como NULL, em vez de 0.
- A expressão "NULL = NULL" é avaliada como NULL, mas na verdade é inválida no SQL; ainda ORDER BY trata NULLs como iguais (o que eles precedem ou seguem valores "regulares" é deixado para o fornecedor do DBMS).
- A expressão "x IS NOT NULL" não é igual a "NOT (x IS NULL)", como é o caso em 2VL.
...
Todos os dialetos SQL implementados comercialmente seguem essa abordagem de 3VL e, portanto, não apenas apresentam esses problemas, mas também apresentam problemas de implementação específicos, que variam entre os produtos .