Подразумеваемое сравнение строк, 0 == '', но 1 == '1'
Я отлаживал что-то и обнаружил некоторую странность в JavaScript:
alert(1=='') ==> false
alert(0=='') ==> true
alert(-1=='') ==> false
Было бы разумно, что подразумеваемое сравнение строк, которое должно быть 0, равно '0'. Это верно для всех ненулевых значений, но почему не для нуля?
Ответы
Ответ 1
В соответствии с документацией Mozilla на Операторы сравнения Javascript
Если два операнда не одного типа, JavaScript преобразует операнды затем применяют строгие сравнение. Если либо операнд является число или логическое значение, операнды преобразован в числа; если операнд - строка, другая - преобразован в строку
Что на самом деле происходит, так это то, что строки преобразуются в числа.
Например:
1 == '1'
становится 1 == Number('1')
становится 1 == 1
: true
Затем попробуйте следующее:
1 == '1.'
становится 1 == Number('1.')
становится 1 == 1
: true
Если бы они становились строками, то вы получили бы '1' == '1.'
, что было бы ложным.
Так получилось, что Number('') == 0
, поэтому 0 == ''
истинно
Ответ 2
Когда javascript делает неявные преобразования типов, пустой литерал строки будет соответствовать целому числу 0. Сделайте свое сравнение таким образом, и вы получите ожидаемый результат:
alert(1==='') ==> false
alert(0==='') ==> false
alert(-1==='') ==> false
Ответ 3
ECMA-262, 3-е издание, 11.9.3 относительно x == y
, шаг 16:
Если Type (x) - Number и Type (y) - String, верните результат сравнения x == ToNumber (y).
Пустая строка ''
перед преобразованием преобразуется в 0
.
Ответ 4
Это всего лишь один из поистине отвратительных маньеров, которые вошли в компромисс JavaScript. '' и 0 - обе неинициализированные значения (равные логическому ложному) и, следовательно, равные.
Чтобы защитить себя от таких странных ошибок, лучше всегда использовать оператор ===.
Ответ 5
Javascript, как и PHP, слабо типизирован *. Поэтому, когда вы сравниваете значение 0 с '', механизм JS преобразует их в аналогичный тип данных. Поскольку 0 и "оба равны логическому (false)," false == false "истинно.
* В слабо типизированных языках переменные не требуют каких-либо конкретных типов данных, поэтому вы можете установить одну переменную в виде строки, изменить ее на int, float и back to string без ошибок метания процессора.
Ответ 6
Во многих языках пустая строка может быть принудительно установлена на false.
Остерегайтесь делать сравнения с == вместо ===:
alert('' == '0'); //false
alert(0 == ''); // true
alert(0 =='0'); // true
== не является транзитивным.