Empresas
Empregos
  • Sobre nós
  • Soluções
    • Publicação de vagas
      Publique sua vaga e receba candidatos qualificados em 48h.
    • Avaliações de candidatos
      Mais de 500 testes técnicos e psicológicos, mais anti-fraude.
    • Headhunting
      Busca executiva personalizada do início ao fim.
    • Folha de Pagamento + EOR
      Dispersão de folha e EOR em mais de 15 países da LATAM.
  • Preços
  • Empregos

0

356
Visualizações
¿Por qué [NaN].includes (NaN) devuelve verdadero en JavaScript?

Estoy familiarizado con NaN siendo "raro" en JavaScript, es decir, NaN === NaN siempre devuelve false , como se describe aquí . Por lo tanto, no se deben hacer comparaciones === para verificar NaN , sino usar isNaN(..) en su lugar.

Así que me sorprendió descubrir que

 > [NaN].includes(NaN) true

Esto parece inconsistente. ¿Por qué tener este comportamiento?

¿Cómo funciona? ¿El método includes comprueba específicamente isNaN ?

over 4 years ago · Santiago Trujillo
5 Respostas
Responde à pergunta

0

Como puede ver al leer la documentación de inclusión, utiliza el algoritmo sameValueZero para funcionar, por lo que, como dice su documentación , proporciona un valor True al comparar NaN y cito:

Podemos ver en la siguiente tabla de comparaciones de igualdad que esto se debe a la forma en que Object.is maneja NaN. Tenga en cuenta que si Object.is(NaN, NaN) se evaluó como falso, podríamos decir que encaja en el espectro flexible/estricto como una forma aún más estricta de triple igual, una que distingue entre -0 y +0. Sin embargo, el manejo de NaN significa que esto no es cierto. Desafortunadamente, Object.is tiene que ser pensado en términos de sus características específicas, en lugar de su laxitud o rigurosidad con respecto a los operadores de igualdad.

over 4 years ago · Santiago Trujillo Relatório

0

El método .includes() usa el algoritmo SameValueZero para verificar la igualdad de dos valores y considera que el valor de NaN es igual a sí mismo.

El algoritmo SameValueZero es similar a SameValue , pero la única diferencia es que el algoritmo SameValueZero considera que +0 y -0 son iguales.

El método Object.is() usa SameValue y devuelve verdadero para NaN .

 console.log(Object.is(NaN, NaN));

El comportamiento del método .includes() es ligeramente diferente del método .indexOf() ; el método .indexOf() usa una comparación de igualdad estricta para comparar valores y la comparación de igualdad estricta no considera que NaN sea igual a sí mismo.

 console.log([NaN].indexOf(NaN));

Puede encontrar información sobre diferentes algoritmos de verificación de igualdad en MDN:

MDN - Comparaciones de igualdad y semejanza

over 4 years ago · Santiago Trujillo Relatório

0

En 7.2.16 Comparación de igualdad estricta , hay la siguiente nota:

NOTA

Este algoritmo difiere del algoritmo SameValue en su tratamiento de ceros con signo y NaN.

Esto significa que Array#includes una función de comparación diferente que para una comparación estricta:

22.1.3.13 Array.prototype.incluye bajo

NOTA 3

El método include difiere intencionalmente del método similar indexOf de dos maneras. En primer lugar, utiliza el algoritmo SameValueZero , en lugar de Strict Equality Comparison , lo que le permite detectar elementos de matriz NaN . En segundo lugar, no omite los elementos de matriz faltantes, en lugar de tratarlos como indefinidos .

over 4 years ago · Santiago Trujillo Relatório

0

Especificaciones

Esto parece ser parte de la operación abstracta Number::sameValueZero :

6.1.6.1.15 Número::mismoValorCero ( x , y )

  1. Si x es NaN e y es NaN , devuelve verdadero .

[...]

Se requiere que esta operación sea parte de la verificación Array#includes() que hace lo siguiente:

22.1.3.13 Array.prototype.includes ( searchElement [ , fromIndex ] )

[...]

  1. Repetir, mientras k < len
    un. Sea elementK el resultado de ? Get( O , ! ToString( k )).
    B. Si SameValueZero( searchElement , elementK ) es verdadero , devuelve verdadero .
    C. Establezca k en k + 1.
  2. Devuelve falso .

[...]

Donde la operación SameValueZero se delegará a la de números en el paso 2:

7.2.12 MismoValorCero ( x , y )

[...]

  1. Si Type( x ) es diferente de Type( y ), devuelve false .
  2. Si Type( x ) es Number o BigInt, entonces
    un. Regreso ! Tipo( x )::mismoValorCero( x , y ).
  3. Regreso ! MismoValorNoNumérico( x , y ).

Para la comparación Array#indexOf() utilizará la comparación de igualdad estricta , por lo que se comporta de manera diferente:

 const arr = [NaN]; console.log(arr.includes(NaN)); // true console.log(arr.indexOf(NaN)); // -1


Otras situaciones similares

Otras operaciones que usan SameValueZero para comparar están en conjuntos y mapas:

 const s = new Set(); s.add(NaN); s.add(NaN); console.log(s.size); // 1 console.log(s.has(NaN)); // true s.delete(NaN); console.log(s.size); // 0 console.log(s.has(NaN)); // false

 const m = new Map(); m.set(NaN, "hello world"); m.set(NaN, "hello world"); console.log(m.size); // 1 console.log(m.has(NaN)); // true m.delete(NaN); console.log(m.size); // 0 console.log(m.has(NaN)); // false


Historia

El algoritmo SameValueZero aparece por primera vez en las especificaciones de ECMAScript 6, pero es más detallado. Todavía tiene el mismo significado y todavía tiene un explícito:

7.2.10 MismoValorCero( x , y )

[...]

  1. Si Tipo( x ) es Número, entonces a. Si x es NaN e y es NaN , devuelve verdadero . [...]

ECMAScript 5.1 solo tiene un algoritmo SameValue que aún trata a NaN igual a NaN . La única diferencia con SameValueZero es cómo se tratan +0 y -0 : SameValue devuelve false para ellos, mientras que SameValueZero devuelve true .

SameValue se usa principalmente para la operación de objetos internos, por lo que es casi intrascendente para escribir código JavaScript. Muchos de los usos de SameValue son cuando se trabaja con claves de objetos y no hay valores numéricos.

La operación SameValue se expone directamente en ECMAScript 6, ya que eso es lo que usa Object.is() :

 console.log(Object.is(NaN, NaN)); // true console.log(Object.is(+0, -0)); // false

De leve interés es que WeakMap y WeakSet también usan SameValue en lugar de SameValueZero que Map y Set usan para comparar. Sin embargo, WeakMap y WeakSet solo permiten objetos como miembros únicos, por lo que intentar agregar un NaN o +0 o -0 u otras primitivas genera un error.

over 4 years ago · Santiago Trujillo Relatório

0

Según el documento de MDN dice que

Nota: Técnicamente hablando, include includes() usa el algoritmo sameValueZero para determinar si se encuentra el elemento dado.

 const x = NaN, y = NaN; console.log(x == y); // false -> using 'loose' equality console.log(x === y); // false -> using 'strict' equality console.log([x].indexOf(y)); // -1 (false) -> using 'strict' equality console.log(Object.is(x, y)); // true -> using 'Same-value' equality console.log([x].includes(y)); // true -> using 'Same-value-zero' equality


Explicación más detallada:

  1. La igualdad del mismo valor cero es similar a la igualdad del mismo valor , pero +0 y −0 se consideran iguales .
  2. El método Object.is() proporciona la igualdad del mismo valor : la única diferencia entre Object.is() y === está en su tratamiento de los ceros con signo y los NaN.

ingrese la descripción de la imagen aquí


Recursos adicionales:

  • ¿Qué operador es igual (== vs ===) debe usarse en las comparaciones de JavaScript?
  • Array.prototype.includes frente a Array.prototype.indexOf
  • ¿+0 y -0 son lo mismo?
over 4 years ago · Santiago Trujillo Relatório
Responde à pergunta
Encontrar trabalhos remotos

Descubra a nova forma de encontrar um emprego!

melhores empregos
Principais categorias de trabalho
Empresas
Postar vaga Preços Comercial
Jurídico
Termos e Condições Política de privacidade
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomende algumas ofertas para mim
Preciso de ajuda