MySQL SELECT uniquement les valeurs non nulles

264

Est-il possible de faire une instruction select qui ne prend que des valeurs NOT NULL?

En ce moment j'utilise ceci:

SELECT * FROM table

Et puis je dois filtrer les valeurs nulles avec une boucle php.

Existe-t-il un moyen de faire:

SELECT * (that are NOT NULL) FROM table

?

En ce moment quand je sélectionne * j'obtiens val1, val2, val3, null, val4, val5, null, null etc .... mais je veux juste obtenir les valeurs qui ne sont pas nulles dans mon résultat. Est-ce possible sans filtrage avec une boucle?

bryan sammon
la source
2
Que voulez-vous qu'il se passe s'il y a une ligne où certaines colonnes ont des valeurs NULL et d'autres colonnes n'ont pas de valeurs NULL?
Mark Byers
Je souhaite obtenir uniquement les valeurs des colonnes qui ne sont pas nulles et ne renvoyer que les valeurs des colonnes de la ligne qui ne sont pas nulles. Actuellement, j'utilise une boucle pour les filtrer, est-il possible de le faire sans boucle?
bryan sammon
1
@bryan - Quelle est la structure de votre table? Toutes les colonnes ont-elles le même type de données?
Martin Smith
1
@bryan - À quoi ressemblerait alors votre ensemble de résultats idéal? Un jeu de résultats à une colonne contenant toutes les valeurs non nulles? Si vous ne modifiez pas votre question avec des exemples de données et les résultats souhaités, cela serait utile ...
Martin Smith
2
@bryan - Il semble que votre table puisse avoir des groupes répétitifs sur plusieurs colonnes? (Voir l'article Wiki pour une explication et une structure alternative suggérée si c'est le cas en.wikipedia.org/wiki/First_normal_form )
Martin Smith

Réponses:

453

Vous devez utiliser IS NOT NULL. (Les opérateurs de comparaison =et les <>deux donnent UNKNOWNavec NULLde chaque côté de l'expression.)

SELECT * 
FROM table 
WHERE YourColumn IS NOT NULL;

Pour être complet, je mentionnerai que dans MySQL, vous pouvez également annuler l' opérateur d'égalité de sécurité nulle, mais ce n'est pas du SQL standard.

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

Modifié pour refléter les commentaires. Il semble que votre table ne soit pas dans sa première forme normale, auquel cas le changement de structure peut vous faciliter la tâche. Quelques autres façons de le faire ...

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*/

L'inconvénient de ce qui précède est qu'il analyse la table plusieurs fois une fois pour chaque colonne. Cela peut être évité par ce qui suit, mais je n'ai pas testé cela dans 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
la source
2
Merci beaucoup .. Ça a aidé :)
DfrDkn
Dans la dernière approche, vous avez utilisé l' CASEinstruction, pas la CASEfonction. Ne devrait-il pas en être ainsi END CASEplutôt que END dans la SELECT CASE ...partie?
Istiaque Ahmed
Pour les personnes moins expertes, pouvez-vous expliquer la dernière solution? La idx rom la première SELECTvient-elle de idxla seconde SELECT? Qu'est-ce que l' CASEénoncé essaie d'accomplir? Que fait SELECTréellement le second ? Et vous faites une jointure intérieure, pas une jointure croisée, non?
Istiaque Ahmed
Je ne pense pas que cela réponde à la question. Cela sonnait comme si OP voulait sélectionner (je suppose une ligne spécifique) mais exclure toutes les colonnes de ce résultat qui étaient nulles - cette réponse vous oblige à spécifier quelles colonnes ne sont pas autorisées à être nulles (ce qui est un problème complètement différent) ou spécifier toutes les colonnes, ne convient pas aux tables avec de nombreuses colonnes
csey
(par exemple quelque chose dans le sens de SELECT * FROM table WHERE * IS NOT NULL AND primary_key="somevalue")
csey
18

Vous pouvez filtrer les lignes contenant une valeur NULL dans une colonne spécifique:

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

Si vous souhaitez filtrer les lignes contenant un null dans n'importe quelle colonne, essayez ceci:

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

Mise à jour: Sur la base de vos commentaires, peut-être voulez-vous cela?

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

Et je suis d'accord avec Martin que si vous devez le faire, vous devriez probablement changer la conception de votre base de données.

Mark Byers
la source
Je ne sais pas si je l'ai expliqué assez bien, mais je vais essayer un peu mieux. En ce moment quand je sélectionne * j'obtiens val1, val2, val3, null, val4, val5, null, null etc .... mais je veux juste obtenir les valeurs qui ne sont pas nulles dans mon résultat. Est-ce possible sans filtrage avec une boucle?
bryan sammon
@bryan - Pourriez-vous expliquer quelles colonnes *retournent? Peut-être fournissez un peu d'exemples de données dans votre question car il n'est pas clair d'après votre commentaire ci-dessus s'il s'agit d'une seule colonne.
Martin Smith
À l'heure actuelle, * renvoie toutes mes valeurs dans la ligne. c'est-à-dire val1, val2, val3, null, val4, val5, null, null. Mais je veux qu'il ne renvoie que les valeurs de colonne qui ne sont pas nulles. À l'heure actuelle, je le fais avec une boucle pour filtrer les valeurs après avoir renvoyé le résultat.
bryan sammon
13
Select * from your_table 
WHERE col1 and col2 and col3 and col4 and col5 IS NOT NULL;

Le seul inconvénient de cette approche est que vous ne pouvez comparer que 5 colonnes, après quoi le résultat sera toujours faux, donc je ne compare que les champs qui peuvent l'être NULL.

Alan Chavez
la source
8

J'ai trouvé cette solution:

Cette requête sélectionne la dernière valeur non nulle pour chaque colonne.

Exemple


Si vous avez une table:

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

vous obtenez:

title|body
t3   |b2

Requete


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

J'espère vous aider.

porquero
la source
GROUP_CONCAT (corps) AS corps
Ravindra Singh
2

J'utilise la \!commande dans MySQL pour extraire les valeurs NULL du shell:

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

Cela fonctionne mieux avec un bon .my.cnfoù votre base de données / nom d'utilisateur / mot de passe est spécifié. De cette façon, vous n'avez qu'à entourer votre selectavec \! mysql eet | grep -v NULL.

soulshake
la source
1

Requête suivante qui fonctionne pour moi

quand j'ai défini la valeur par défaut de la colonne 'NULL' alors

select * from table where column IS NOT NULL

et quand j'ai mis rien par défaut alors

select * from table where column <>''
Basant
la source
0

Oui, utilisez NOT NULLdans votre requête comme ci-dessous.

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

MYSQL N'EST PAS NUL AVEC JOINS ET SELECT, INSÉRER DANS, SUPPRIMER ET OPÉRATEUR LOGIQUE COMME OU, NON

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;
Développeur
la source
-4
SELECT * FROM TABLE_NAME
where COLUMN_NAME <> '';
Venkat Kallem
la source
2
Ce n'est pas sélectionner ceux qui sont vides. la question est de sélectionner des valeurs non nulles
krishna