Двойные восклицательные знаки?
Возможный дубликат:
Что !! (не нет) оператор в JavaScript?
Что это !! оператор (двойной восклицательный знак) означает в JavaScript?
Итак, я отлаживал некоторый код и наткнулся на это:
var foo.bar = 0; // this is actually passed from another function, adding it for context
function(foo) {
var someVar = !!foo.bar;
if (foo.bar) {
// ..stuff happens
} else {
// .. something else happens
}
}
Хорошо, мои вопросы в чем смысл !!
? Все, что делает, это делает 0 === false
.
-
Есть ли польза от использования этого по сравнению с boolean(foo.bar)
?
-
foo.bar может быть оценен в if как есть, потому что 0 === false
уже, так зачем проходить преобразование? (someVar больше нигде не используется)
Ответы
Ответ 1
Это преобразует значение в логическое значение и обеспечивает логический тип.
"foo" // Evaluates to "foo".
!"foo" // Evaluates to false.
!!"foo" // Evaluates to true.
Если foo.bar
пропущен, то это может быть не 0, а какое-то другое ложное значение. Смотрите следующую таблицу истинности:
Таблица правды для JavaScript
'' == '0' // false
0 == '' // true
0 == '0' // true
false == 'false' // false
false == '0' // true
false == undefined // false
false == null // false
null == undefined // true
" \t\r\n" == 0 // true
Источник: Даг Крокфорд
Javascript также становится очень странным, когда дело доходит до значений NaN. И это единственный случай, когда я могу придумать, где это возможно! будет вести себя иначе, чем ===.
NaN === NaN //false
!!NaN === !!NaN //true
// !!NaN is false
Ответ 2
Я думаю, что ответ заключается в том, что на самом деле нет особого смысла. Мы можем рассказать о том, как это произошло:
- возможно, более ранняя версия функции, используемой
someVar
в нескольких местах, или способами, которые действительно выиграли от наличия true
или false
, поэтому это имело больше смысла.
- Возможно, тот, кто написал эту функцию, так привык использовать
!!
для преобразования в true
/false
, что он даже не заметил, что здесь не нужно.
- Возможно, человек, который написал функцию, считает, что каждому вычислению (в данном случае, логическому преобразованию) должно быть присвоено значащее имя, назначая некоторую переменную его результату.
- возможно, поскольку булево преобразование в JavaScript удивительно подвержено ошибкам (в том, что, например,
new Boolean(false)
является истиннозначным значением), человек, который написал функцию, чувствует, что он всегда должен выполняться явно, а не неявно — хотя эффект тот же самый; просто обратить внимание на него как на потенциальную ошибку.
- это, конечно, предполагает, что человек, который написал эту функцию, думает о
!!
как "явное" логическое преобразование. Технически это не так. он использует одно и то же неявное логическое преобразование, которое if
делает — но если вы привыкли к этой идиоме, то это означает явное преобразование.
но по моему субъективному мнению ни одна из этих причин не очень хорошая!
Ответ 3
Как указано выше, он заставляет объект с булевым типом. Вы можете сами убедиться:
(function typecheck() {
var a = "a";
var b = !a;
var c = !!a;
alert("var a = " + typeof(a) + "\n" +
"var b = " + typeof(b) + "\n" +
"var c = " + typeof(c));
})();
Если вы просто выполняете сравнения, преобразование просто сохраняет ваше принуждение типа позже.
FYI, следующие значения принудительно приводятся к FALSE в JavaScript: