Tout d'abord, je tiens à mentionner que je sais comment isNaN()
et Number.isNaN()
travaille. Je lis le guide défini de David Flanagan et il donne un exemple pour savoir comment vérifier si la valeur est NaN
:
x !== x
Cela se traduira par true
si et seulement si x
est NaN
.
Mais maintenant, j'ai une question: pourquoi utilise-t-il une comparaison stricte? Parce qu'il semble que
x != x
se comporte de la même manière. Est-il sûr d'utiliser les deux versions, ou il me manque une ou plusieurs valeurs dans JavaScript qui retourneront true
pour x !== x
et false
pour x != x
?
javascript
nan
Giorgi Nakeuri
la source
la source
!==
chèques aux!=
chèques. Autant que je sache, il n'y a pas d'autre valeur oùx != x
. Mais il existe deux groupes distincts de développeurs JavaScript: ceux qui préfèrent!=
et ceux qui préfèrent!==
, que ce soit pour la vitesse, la clarté, l'expressivité, etc.NaN
n'est pas un type unique, c'est un nombre. C'est une valeur unique qui n'est pas égale à elle-même.===
avec NaN pour faire valoir que NaN n'est pas égal à lui-même. Il n'a pas «tort», il le fait comme un exercice d'enseignement, démontrant que cela ne fonctionne pas.Réponses:
Tout d'abord, permettez-moi de souligner que
NaN
c'est une valeur très spéciale: par définition, elle n'est pas égale à elle-même. Cela vient de la norme IEEE-754 sur laquelle s'appuient les numéros JavaScript. La valeur "pas un nombre" n'est jamais égale à elle-même, même lorsque les bits correspondent exactement. (Ce qu'ils ne sont pas nécessairement dans IEEE-754, cela permet plusieurs valeurs différentes "pas un nombre".) C'est pourquoi cela arrive même; toutes les autres valeurs en JavaScript sont égales à elles-mêmes,NaN
c'est juste spécial.Non, tu ne l'es pas. La seule différence entre
!==
et!=
est que ce dernier effectuera une coercition de type si nécessaire pour que les types des opérandes soient identiques. Dansx != x
, les types d'opérandes sont les mêmes, et donc exactement les mêmes quex !== x
.Ceci est clair dès le début de la définition de l' opération abstraite d'égalité :
Les deux premières étapes sont la plomberie de base. Donc, en fait, la toute première étape
==
est de voir si les types sont les mêmes et, si c'est le cas, de le faire à la===
place.!=
et ne!==
sont que des versions niées de cela.Donc, si Flanagan a raison, cela ne
NaN
donnera vrai que pourx !== x
, nous pouvons être sûrs qu'il est également vrai que seulNaN
donnera vrai pourx != x
.De nombreux programmeurs JavaScript utilisent par défaut
===
et!==
pour éviter certains pièges autour de la contrainte de type que font les opérateurs lâches, mais il n'y a rien à lire dans l'utilisation par Flanagan de l'opérateur strict vs lâche dans ce cas.la source
4.9.1 - Equality and Inequality Operators
section et cela semble être la réponse. Le point clé de===
comparaison est:If the two values have the same type, test them for strict equality as described above. If they are strictly equal, they are equal. If they are not strictly equal, they are not equal
.a
est en fait une fonction et ne renvoie pas deux fois la même valeur? Ce n'est pas la même chose qu'une valeur pour laquelle!==
serait vraie, ce que le PO a demandé. C'est juste une fonction qui renvoie des valeurs différentes.foo() !== foo()
n'est pas nécessairement vrai non plus, car ilfoo
peut renvoyer des valeurs différentes à chaque appel.Pour les besoins de NaN,
!=
et!==
faites la même chose.Cependant, de nombreux programmeurs évitent
==
ou!=
en JavaScript. Par exemple, Douglas Crockford les considère parmi les « mauvaises parties » du langage JavaScript car ils se comportent de manière inattendue et déroutante:la source
Juste pour le plaisir, laissez-moi vous montrer un exemple artificiel où il
x
n'y en a pas,NaN
mais les opérateurs se comportent de toute façon différemment. Définissez d'abord:Ensuite nous avons
mais
la source
foo() != foo()
là que foo renvoie 1 puis 2. Par exemple, les valeurs ne sont pas les mêmes, il s'agit simplement de comparer des valeurs différentes.Je veux juste souligner que ce
NaN
n'est pas la seule chose qui produitx !== x
sans utiliser l'objet global. Il existe de nombreuses façons intelligentes de déclencher ce comportement. En voici un utilisant des getters:Comme d'autres réponses le soulignent,
==
effectue la coersion de type, mais comme dans d'autres langages et par la norme - NaN indique un échec de calcul, et pour de bonnes raisons n'est pas égal à lui-même.Pour une raison autre que moi, les gens considèrent que c'est un problème avec JS, mais la plupart des langages qui ont des doubles (à savoir, C, Java, C ++, C #, Python et autres) présentent ce comportement exact et les gens sont très bien avec cela.
la source
Comme parfois, les images valent mieux que les mots, vérifiez ce tableau (ce qui est la raison pour laquelle j'en fais une réponse plutôt qu'un commentaire, c'est parce qu'il obtient une meilleure visibilité).
Là, vous pouvez voir que la comparaison d'égalité stricte (===) ne renvoie vrai que si le type et le contenu correspondent, donc
Alors que la comparaison d'égalité abstraite (==) vérifie uniquement le contenu * en convertissant des types puis en les comparant strictement:
Bien que ce ne soit pas clair, sans consulter l' ECMA , ce que JavaScript prend en compte lors de la comparaison, d'une manière que le code ci-dessous évalue à vrai.
la source