LNNVL é uma função integrada do oracle que retorna TRUE para condições avaliadas como FALSE ou UNKNOWN e retorna FALSE para condições avaliadas como TRUE. Minha pergunta é qual seria o benefício de retornar o oposto da condição de verdade, em vez de apenas manipular os valores NULL?
Por exemplo, suponha que você tenha uma tabela Emp com as colunas StartCommission e CurrentCommission que podem conter nulos. O seguinte retorna apenas linhas com nenhum valor nulo:
SELECT * FROM Emp WHERE StartCommission = CurrentCommission;
Se você deseja incluir linhas em que qualquer comissão é nula, você pode fazer algo assim:
SELECT * FROM Emp WHERE StartCommission = CurrentCommission
OR StartCommission IS NULL OR CurrentCommission IS NULL;
Parece que existiria uma função para reduzir essa sintaxe, mas o uso de LNNVL retorna todos os registros diferentes e todos os registros com valores nulos.
SELECT * FROM Emp WHERE LNNVL(StartCommission = CurrentCommission);
A adição de NOT a isso retorna apenas linhas sem nulos. Parece-me que a funcionalidade desejada para este caso seria manter verdadeiras condições verdadeiras, falsas condições falsas e avaliar condições verdadeiras como verdadeiras. Eu realmente criei um caso de uso baixo aqui? É realmente mais provável querer transformar desconhecido em verdadeiro, verdadeiro em falso e falso em verdadeiro?
create table emp (StartCommission Number(3,2), CurrentCommission Number(3,2));
insert into emp values (null,null);
insert into emp values (null,.1);
insert into emp values (.2,null);
insert into emp values (.3,.4);
fonte
Respostas:
É uma função estranha com uma história estranha - mas o nvl2 também é estranho.
lnnvl
é basicamente umis not true
operador - sem dúvida, pode ser usado da melhor maneiranvl2
possível, mas quando você precisa procurar uma função toda vez que a usa para lembrá-lo exatamente do que faz, fica se perguntando se é melhor seguirnvl
,coalesce
,decode
enullif
, juntamente comcase
expressões, que são mais intuitivosfonte
nullif
até perceber que pode ser uma grande ajuda para fazer 'divisão por zero' = nulo. Você realmente acha que o nvl2 (a, c, b) é muito melhor do que decodificar (a, null, b, c)?Em outras palavras, ainda não usei o LNNVL em meus vários anos de programador de DBA e PL / SQL. Eu usei o NVL2 de vez em quando (e sempre tive que procurar de que lado era verdade e de que lado não era). Nesse ponto, parece melhor, do ponto de vista da legibilidade, acabar usando NVL, DECODE, CASE etc.,
Como alternativa, isso funciona, supondo que se tenha uma boa noção de como o Oracle lida com NULLs e aritmética, mas a essa altura, pode-se também usar sua consulta original para facilitar a leitura (e o plano de execução também pode sofrer mais):
fonte
StartCommission<>CurrentCommission OR StartCommission + CurrentCommission IS NULL
?lnnvl
.