MySQL SELECT apenas valores não nulos

264

É possível fazer uma instrução select que use apenas valores NOT NULL?

Agora eu estou usando isso:

SELECT * FROM table

E então eu tenho que filtrar os valores nulos com um loop php.

Existe uma maneira de fazer:

SELECT * (that are NOT NULL) FROM table

?

Agora, quando eu seleciono * eu recebo val1, val2, val3, nulo, val4, val5, nulo, nulo etc .... mas eu só quero obter os valores que não são nulos no meu resultado. Isso é possível sem filtrar com um loop?

bryan sammon
fonte
2
O que você deseja que aconteça se houver uma linha em que algumas colunas tenham valores NULL e outras não tenham valores NULL?
Mark Byers
Gostaria de obter apenas os valores das colunas que não são nulos e retornar apenas os valores da coluna na linha que não são nulos. No momento, eu uso um loop para filtrá-los, é possível fazer isso sem um loop?
Bryan sammon # 12/11
1
@ bryan - Qual é a sua estrutura de tabelas? Todas as colunas têm o mesmo tipo de dados?
Martin Smith
1
@ bryan - Então, como seria o seu conjunto de resultados ideal? Um conjunto de resultados de uma coluna contendo todos os valores não nulos? Se não editar a sua pergunta com exemplos de dados e resultados desejados seria útil ...
Martin Smith
2
@bryan - Parece que sua tabela pode ter grupos repetidos em colunas? (Veja o artigo Wiki para uma explicação e uma estrutura alternativa sugerida, se for esse o caso en.wikipedia.org/wiki/First_normal_form )
Martin Smith

Respostas:

453

Você deveria usar IS NOT NULL. (Os operadores de comparação =e os <>dois fornecem UNKNOWNcom NULLambos os lados da expressão.)

SELECT * 
FROM table 
WHERE YourColumn IS NOT NULL;

Apenas para completar, mencionarei que no MySQL você também pode negar o operador de igualdade segura nula, mas esse não é o SQL padrão.

SELECT *
FROM table 
WHERE NOT (YourColumn <=> NULL);

Editado para refletir os comentários. Parece que sua tabela pode não estar na primeira forma normal; nesse caso, alterar a estrutura pode facilitar sua tarefa. Algumas outras maneiras de fazer isso ...

SELECT val1 AS val
FROM  your_table
WHERE val1 IS NOT NULL
UNION ALL
SELECT val2 
FROM  your_table
WHERE val2 IS NOT NULL
/*And so on for all your columns*/

A desvantagem do acima é que ela varre a tabela várias vezes uma vez para cada coluna. Isso pode ser evitado pelo abaixo, mas eu não testei isso no MySQL.

SELECT CASE idx
         WHEN 1 THEN val1
         WHEN 2 THEN val2
       END AS val
FROM   your_table
        /*CROSS JOIN*/
       JOIN (SELECT 1 AS idx
                   UNION ALL
                   SELECT 2) t
HAVING val IS NOT NULL  /*Can reference alias in Having in MySQL*/
Martin Smith
fonte
2
Muito obrigado .. Ele ajudou :)
DfrDkn
Na última abordagem, você usou a CASEinstrução, não a CASEfunção. Então não deveria ser END CASE, em vez de END na SELECT CASE ...parte?
Istiaque Ahmed
Para pessoas não tão especializadas, você pode explicar a última solução? O idx rom o primeiro SELECTvem do idxno segundo SELECT? O que a CASEdeclaração tenta realizar? O que o segundo SELECTrealmente faz? E você está fazendo uma junção interna, não uma junção cruzada, certo?
Istiaque Ahmed
Eu não acho que isso responda à pergunta. Parecia que o OP queria selecionar (presumo uma específica) linha, mas excluir todas as colunas desse resultado que eram nulas - essa resposta requer que você especifique quais colunas não podem ser nulas (que é um problema completamente diferente) ou especificar todas as colunas, inadequados para tabelas com muitas colunas
csey
(por exemplo, algo ao longo das linhas de SELECT * FROM table WHERE * IS NOT NULL AND primary_key="somevalue")
csey
18

Você pode filtrar as linhas que contêm um valor NULL em uma coluna específica:

SELECT col1, col2, ..., coln
FROM yourtable
WHERE somecolumn IS NOT NULL

Se você deseja filtrar as linhas que contêm um nulo em qualquer coluna, tente o seguinte:

SELECT col1, col2, ..., coln
FROM yourtable
WHERE col1 IS NOT NULL
AND col2 IS NOT NULL
-- ...
AND coln IS NOT NULL

Atualização: Com base nos seus comentários, talvez você queira isso?

SELECT * FROM
(
    SELECT col1 AS col FROM yourtable
    UNION
    SELECT col2 AS col FROM yourtable
    UNION
    -- ...
    UNION
    SELECT coln AS col FROM yourtable
) T1
WHERE col IS NOT NULL

E eu concordo com Martin que se você precisar fazer isso, provavelmente deverá alterar o design do banco de dados.

Mark Byers
fonte
Não sei se expliquei bem o suficiente, mas vou tentar um pouco melhor. Agora, quando eu seleciono * eu recebo val1, val2, val3, nulo, val4, val5, nulo, nulo etc .... mas eu só quero obter os valores que não são nulos no meu resultado. Isso é possível sem filtrar com um loop?
Bryan sammon 12/03/11
@ bryan - Você poderia explicar quais colunas *retornam? Talvez forneça alguns exemplos de dados na sua pergunta, pois não está claro no seu comentário acima se esta é apenas uma coluna.
Martin Smith
No momento, * retorna todos os meus valores na linha. ou seja, val1, val2, val3, nulo, val4, val5, nulo, nulo. Mas eu quero que ele retorne apenas os valores da coluna que não são nulos. No momento, faço isso com um loop para filtrar os valores após o retorno do resultado.
Bryan sammon 12/03/11
13
Select * from your_table 
WHERE col1 and col2 and col3 and col4 and col5 IS NOT NULL;

A única desvantagem dessa abordagem é que você pode comparar apenas cinco colunas; depois disso, o resultado sempre será falso; portanto, comparo apenas os campos que podem ser NULL.

Alan Chavez
fonte
8

Encontrei esta solução:

Esta consulta seleciona o último valor não nulo para cada coluna.

Exemplo


Se você tem uma mesa:

id|title|body
1 |t1   |b1
2 |NULL |b2
3 |t3   |NULL

você obtém:

title|body
t3   |b2

Inquerir


SELECT DISTINCT (

  SELECT title
  FROM test
  WHERE title IS NOT NULL 
  ORDER BY id DESC 
  LIMIT 1
) title, (

  SELECT body
  FROM test
  WHERE body IS NOT NULL 
  ORDER BY id DESC 
  LIMIT 1
) body
FROM test

Espero te ajudar.

porquero
fonte
GROUP_CONCAT (body) AS body
Ravindra Singh
2

Eu uso o \!comando no MySQL para receber valores NULL do shell:

\! mysql -e "SELECT * FROM table WHERE column = 123456\G" | grep -v NULL

Funciona melhor com um local apropriado .my.cnfonde seu banco de dados / nome de usuário / senha são especificados. Dessa forma, você só precisa cercar o seu selectcom \! mysql ee | grep -v NULL.

aperto de mão
fonte
1

Após a consulta trabalhar para mim

quando eu tiver definido o valor padrão da coluna 'NULL', então

select * from table where column IS NOT NULL

e quando eu definir o valor padrão nada, então

select * from table where column <>''
Basant
fonte
0

Sim, use NOT NULLem sua consulta como esta abaixo.

SELECT * 
FROM table
WHERE col IS NOT NULL;
Jonathan Vasiliou
fonte
0

O MYSQL NÃO É NULL COM JUNTAS E SELECIONA, INSERIR, EXCLUIR E OPERADOR LÓGICO COMO OU, NÃO

Using IS NOT NULL On Join Conditions

 SELECT * FROM users 
 LEFT JOIN posts ON post.user_id = users.id 
 WHERE user_id IS NOT NULL;

 Using IS NOT NULL With AND Logical Operator

 SELECT * FROM users 
 WHERE email_address IS NOT NULL 
 AND mobile_number IS NOT NULL;

Using IS NOT NULL With OR Logical Operator

 SELECT * FROM users 
 WHERE email_address IS NOT NULL 
 OR mobile_number IS NOT NULL;
Desenvolvedor
fonte
-4
SELECT * FROM TABLE_NAME
where COLUMN_NAME <> '';
Venkat Kallem
fonte
2
Não é possível selecionar quais estão vazios. questão é para a selecção de valores não nulos
Krishna