Por que “true” == true mostra falso em JavaScript?


90

MDC descreve o ==operador da seguinte maneira :

Se os dois operandos não forem do mesmo tipo, JavaScript os converte e aplica a comparação estrita. Se o operando for um número ou booleano, os operandos serão convertidos em números, se possível; else se qualquer operando for uma string, o outro operando é convertido em uma string, se possível.

Com isso em mente, eu avaliaria o "true" == trueseguinte:

  1. Eles são do mesmo tipo? Não
  2. O operando é um número ou booleano? sim
  3. Podemos converter ambos em um número? Não ( isNaN(Number("true")) // true)
  4. Qualquer um dos operandos é uma string? sim
  5. Podemos converter o outro operando em uma string? Sim ( String(true) === "true" // true)

Acabei com as strings "true"e "true", que deve avaliar como true, mas o JavaScript mostra falso.

O que eu perdi?



6
Com tanto JavaScript por aí, o mundo é um lugar assustador: if("true" == true) {console.log("yes")} else {console.log("no")}; if("true") {console.log("yes")} else {console.log("no")}---> "não sim"
user1068352

1
Devo dizer que estou surpreso, e é tão estúpido que isso aconteça. Mais uma razão para sempre sempre usar ===
BT

Respostas:


89

Porque "true"é convertido para NaN, enquanto trueé convertido para 1. Então eles são diferentes.

Como você relatou, ambos são convertidos em números, porque pelo menos truepodem ser (veja o comentário de Erik Reppen), e depois comparados.


Você pode me dizer quando o passo Can we convert both to a number?será falso então? Se par NaNfor um número, como essa etapa pode falhar?
Isaac

5
Qualquer um contra nenhum. Se ambos resultassem em NaN, eles mudariam para avaliação de string. Se apenas um pode ser convertido, ainda há uma comparação numérica.
Erik Reppen

2
Na verdade, existem alguns objetos estranhos em Javascript que se comportam de maneira bastante estranha. Por exemplo, documentos XML no IE <9 geram um erro quando você tenta convertê-los em números.
MaxArt

Você mesmo pode ver as conversões fazendo Number(true)eNumber('true')
Erik Reppen

11

O ==operador de comparação é definido no ECMA 5 como:

  1. Se Type (x) for Number e Type (y) for String,
    retorne o resultado da comparação x == ToNumber (y).
  2. Se Type (x) for String e Type (y) for Number,
    retorne o resultado da comparação ToNumber (x) == y.
  3. Se Type (x) for Boolean, retorne o resultado da comparação ToNumber (x) == y.
  4. Se Type (y) for Boolean, retorne o resultado da comparação x == ToNumber (y).

Portanto, "true" == true é avaliado como:

  1. "true" == ToNumber (true)   (via regra 7)
  2. "verdadeiro" == 1
  3. ToNumber ("true") == 1   (via regra 5)
  4. NaN == 1

===> falso


Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.