Firebird Documentation IndexGuide Firebird et NULL → NULL dans les expressions
Firebird Home Firebird Home Précédent: Qu'est ce que NULL?Firebird Documentation IndexNiveau supérieur: Guide Firebird et NULLSuivant: NULL dans les UDFs

NULL dans les expressions

Expressions retournant NULL
NULL dans des expressions booléennes
Plus de logique (ou pas)
NULL dans des fonctions d'agrégat

Combien d'entre nous ont appris à leurs dépends que NULL est contagieux: utilisez le dans une expression numérique, de chaîne de caractère ou de date/heure, et le résultat sera toujours NULL. Utilisez le dans une expression booléenne, et le résultat dépendra du type d' opération et des autres valeurs impliquées.

Notez au passage que dans les versions de Firebird avant 2.0, il est le plus souvent illégal d'utiliser la constante NULL directement dans des opérations ou comparaisons. Partout où vous verrez NULL dans les instructions suivantes, lisez le comme « un champ, une variable ou une autre expression renvoyant NULL ».

Expressions retournant NULL

Les expressions dans cette liste renvoient toujours NULL:

  • 1 + 2 + 3 + NULL

  • 'Home ' || 'sweet ' || NULL

  • MyField = NULL

  • MyField <> NULL

  • NULL = NULL

  • not (NULL)

Si vous avez des difficultés à comprendre pourquoi, souvenez vous que NULL signifie « indéterminé ». Regardez aussi le tableau suivant où des explications sont données au cas par cas. Dans le tableau nous n'écrivons pas NULL dans les expressions (comme dit plus haut, c'est souvent interdit); à la place, nous utilisons deux entités A et B qui sont toutes deux NULL. A et B peuvent être des champs, des variables, ou des sous-expressions - du moment quelles sont NULL, elles ont le même comportement dans les expressions utilisées.

Tableau 1. Opérations des entités A et B null

Si A et B sont NULL, alors: Est: Parce que:
1 + 2 + 3 + A NULL Si A est indéterminée, alors 6 + A est aussi indéterminée.
'Home ' || 'sweet ' || A NULL Si A est indéterminée, 'Home sweet ' || A est aussi indéterminée.
MonChamp = A NULL Si A est indéterminée, vous ne pouvez dire si MonChamp à la même valeur...
MonChamp <> A NULL ...mais vous ne pouvez non plus dire si MonChamp à une valeur différente !
A = B NULL Avec A et B indéterminées, il est impossible de savoir si elles sont égales.
not (A) NULL Si A est indéterminée, sa négation est aussi indéterminée.


NULL dans des expressions booléennes

Non avons déjà vu que not(NULL) renvoie NULL. Pour les opérateurs and et or , les choses sont un peu plus compliquées :

  • NULL or false = NULL

  • NULL or true = true

  • NULL or NULL = NULL

  • NULL and false = false

  • NULL and true = NULL

  • NULL and NULL = NULL

Le SQL Firebird n'a pas de type booléen; les constantes true et false n'existent pas. Dans la colonne de gauche du tableau suivant, (true) et (false) représentent des expressions renvoyant true/false.

Tableau 2. Opérations booléennes sur une entité A null

Si A est NULL, alors: Est: Parce que:
A or (false) NULL « A or false » a toujours la même valeur que A - qui est indéterminée.
A or (true) true « A or true » est toujours true - la valeur de A n'a pas d'importance.
A or A NULL « A or A » est toujours égal à A - qui est NULL.
A and (false) false « A and false » est toujours false - la valeur de A n'a pas d'importance.
A and (true) NULL « A and true » a toujours la même valeur que A - qui est indéterminée.
A and A NULL « A and A » est toujours égal à A - qui est NULL.


Tous ces résultats sont en accord avec la logique booléenne. Le fait que, pour calculer « X or true » et « X and false », vous n'ayez simplement pas besoin de connaitre la valeur de X, fait partie des bases d'une fonctionnalité que nous connaissons dans divers langages de programmation : l'évaluation booléenne rapide.

Plus de logique (ou pas)

Les résultats obtenus ci-dessus pourraient vous mener aux idées suivantes :

  • 0 fois x égal 0 pour tout x. En conséquence, même si la valeur de x est indéterminée, 0 * x égal 0. (Note: ceci seulement si x est d'un type n'acceptant que des nombres, pas NaN ou infini.)

  • Un chaîne vide est classée lexicographiquement avant toute autre chaîne. Donc, S >= '' est vrai quelque soit la valeur de S.

  • Chaque valeur est égale à elle même, qu'elle soit connue ou pas. Donc, bien que A = B renvoie NULL si A et B sont des entités NULL différentes, A = A devrait toujours retourner true, même si A est NULL.

Comment cela est-il implémenté dans le SQL de Firebird ? Et bien, je suis désolé de vous dire qu'en dépit de toute cette logique - et les analogies avec les résultats booléens discutés ci-dessus - toutes ces expressions renvoient NULL:

  • 0 * NULL

  • NULL >= ''

  • '' <= NULL

  • A = A (avec A comme champ ou variable null)

Et voilà pour la logique.

NULL dans des fonctions d'agrégat

Dans des fonctions d'agrégat comme COUNT, SUM, AVG, MAX, et MIN, NULL est géré différemment: pour calculer le résultat, seuls les champs non-NULL sont pris en considération. C'est à dire que, si vous avez cette table:

MyTable
ID Name Amount
1 John 37
2 Jack <NULL>
3 Joe 5
4 Josh 12
5 Jay <NULL>

...l'instruction select sum(Amount) from MyTable renvoie 54, qui est 37 + 5 + 12. Si les cinq champs avaient été additionnés, le résultat aurait été NULL. Pour AVG, les champs non-NULL sont additionnés et la somme est divisée par le nombre de champs non-NULL .

Il y a seulement une exception à cette règle: COUNT(*) renvoie le dénombrement de toutes les lignes, même celles pour lesquelles les champs sont NULL. Mais COUNT(FieldName) se comporte comme les autres fonctions d'agrégat et ne compte que les enregistrements pour lesquels le champ spécifié est non NULL.

Une autre chose à savoir est que COUNT(*) et COUNT(FieldName) ne renvoient jamais NULL: s'il n'y a pas d'enregistrement dans l'ensemble de données les deux fonctions renvoient 0. Ainsi, COUNT(FieldName) renvoie 0 si tous les champs FieldName dans l'ensemble de données sont NULL. Les autres fonctions d'agrégat renvoient NULL dans ce cas. Faites attention que même SUM renvoie NULL s'il est utilisé sur un ensemble vide, ce qui est contraire à la logique commune.

Précédent: Qu'est ce que NULL?Firebird Documentation IndexNiveau supérieur: Guide Firebird et NULLSuivant: NULL dans les UDFs
Firebird Documentation IndexGuide Firebird et NULL → NULL dans les expressions