Почему alert (!! "0" ) и alert (false == "0" ) оба выводят true в JavaScript

Насколько я знаю в JavaScript! предполагается нормализовать логическое значение, преобразующее его в true или false из другого типа. Это означало бы, что "0" преобразуется в логическое значение true. С другой стороны, если я сравниваю это с ложным, оказывается, что он фактически является ложным (как результат сравнения). Какое правило я не вижу здесь. Я тестировал его в IE и Opera.

Ответ 1

Оператор == проверяет свободное равенство, которое не имеет ничего общего с правдой.

В частности, он преобразует в операнды цифры, а затем сравнивает числа.
Строки, содержащие числа, преобразуются в числа, которые они содержат; booleans преобразуются в 0 и 1.
Объекты преобразуются путем вызова valueOf, если они определены.

Таким образом, все следующее верно:

  • "1" == 1
  • "0" == false
  • "1" == true
  • "2" != true
  • "2" != false
  • ({ valueOf:function() { return 2; } }) == 2
  • ({ valueOf:function() { return 1; } }) == true

Ответ 2

В первом случае непустая строка эквивалентна true.

Во втором случае, поскольку один операнд является логическим, оба операнда преобразуются в числовые значения. Я полагаю, что false преобразуется в числовое значение 0, а строка "0" также преобразуется в числовое значение 0, в результате получается 0 == 0, которое истинно.

Ознакомьтесь с ссылкой Mozilla для поведения оператора.

Ответ 3

Для первого выражения раздел 9.2 ECMA-262 определяет абстрактную операцию ToBoolean, внутренне используемую логическим оператором NOT. В нем говорится:

Строка
Результат - false, если аргументом является пустая строка (ее длина равна нулю); иначе результат будет правдой.

Для второго выражения JavaScript выполнит принуждение типа при попытке сравнить эти значения разных типов данных. Дуглас Крокфорд говорит, что это ошибка. Было бы неверным, если бы вы использовали === вместо ==. Правила довольно сложны, поэтому вы должны непосредственно посмотреть в разделе 11.9.3 ECMA-262 для деталей.