空数组为真,但也等于假。
Var arr = []; console.log(数组:,arr); if (arr) console.log("这是真的!"); if (arr == false) console.log("这是假的!"); 如果(arr & & arr = = false) console.log(“……什么? ?”);
我猜这是由于由等式运算符进行的隐式转换。
有人能解释一下幕后发生了什么吗?
空数组为真,但也等于假。
Var arr = []; console.log(数组:,arr); if (arr) console.log("这是真的!"); if (arr == false) console.log("这是假的!"); 如果(arr & & arr = = false) console.log(“……什么? ?”);
我猜这是由于由等式运算符进行的隐式转换。
有人能解释一下幕后发生了什么吗?
当前回答
你在这里测试不同的东西。
if (arr)调用对象(数组是对象在JS中的实例)将检查对象是否存在,并返回true/false。
当你调用if (arr == false)时,你比较这个对象的值和原始的false值。在内部,调用了arr.toString(),它返回一个空字符串“”。
这是因为在Array上调用toString会返回Array.join(),而空字符串是JavaScript中的一个假值。
其他回答
例子:
const array = []
const boolValueOfArray = !!array // true
它的发生是因为
ToNumber(ToPrimitive([])) == ToNumber(false)
[]为空数组对象→ToPrimitive([])→""→ToNumber("")→0 tonnumber (false)→0 0 == 0→true
console.log('-- types: undefined, boolean, number, string, object --');
console.log(typeof undefined); // undefined
console.log(typeof null); // object
console.log(typeof NaN); // number
console.log(typeof false); // boolean
console.log(typeof 0); // number
console.log(typeof ""); // string
console.log(typeof []); // object
console.log(typeof {}); // object
console.log('-- Different values: NotExist, Falsy, NaN, [], {} --');
console.log('-- 1. NotExist values: undefined, null have same value --');
console.log(undefined == null); // true
console.log('-- 2. Falsy values: false, 0, "" have same value --');
console.log(false == 0); // true
console.log(false == ""); // true
console.log(0 == ""); // true
console.log('-- 3. !NotExist, !Falsy, and !NaN return true --');
console.log(!undefined); // true
console.log(!null); // true
console.log(!false); // true
console.log(!""); // true
console.log(!0); // true
console.log(!NaN); // true
console.log('-- 4. [] is not falsy, but [] == false because [].toString() returns "" --');
console.log(false == []); // true
console.log([].toString()); // ""
console.log(![]); // false
console.log('-- 5. {} is not falsy, and {} != false, because {}.toString() returns "[object Object]" --');
console.log(false == {}); // false
console.log({}.toString()); // [object Object]
console.log(!{}); // false
console.log('-- Comparing --');
console.log('-- 1. string will be converted to number or NaN when comparing with a number, and "" will be converted to 0 --');
console.log(12 < "2"); // false
console.log("12" < "2"); // true
console.log("" < 2); // true
console.log('-- 2. NaN can not be compared with any value, even if NaN itself, always return false --');
console.log(NaN == NaN); // false
console.log(NaN == null); // false
console.log(NaN == undefined); // false
console.log(0 <= NaN); // false
console.log(0 >= NaN); // false
console.log(undefined <= NaN); // false
console.log(undefined >= NaN); // false
console.log(null <= NaN); // false
console.log(null >= NaN); // false
console.log(2 <= "2a"); // false, since "2a" is converted to NaN
console.log(2 >= "2a"); // false, since "2a" is converted to NaN
console.log('-- 3. undefined can only == null and == undefined, and can not do any other comparing even if <= undefined --');
console.log(undefined == null); // true
console.log(undefined == undefined); // true
console.log(undefined == ""); // false
console.log(undefined == false); // false
console.log(undefined <= undefined); // false
console.log(undefined <= null); // false
console.log(undefined >= null); // false
console.log(0 <= undefined); // false
console.log(0 >= undefined); // false
console.log('-- 4. null will be converted to "" when <, >, <=, >= comparing --');
console.log(12 <= null); // false
console.log(12 >= null); // true
console.log("12" <= null); // false
console.log("12" >= null); // true
console.log(0 == null); // false
console.log("" == null); // false
console.log('-- 5. object, including {}, [], will be call toString() when comparing --');
console.log(12 < {}); // false, since {}.toString() is "[object Object]", and then converted to NaN
console.log(12 > {}); // false, since {}.toString() is "[object Object]", and then converted to NaN
console.log("[a" < {}); // true, since {}.toString() is "[object Object]"
console.log("[a" > {}); // false, since {}.toString() is "[object Object]"
console.log(12 < []); // false, since {}.toString() is "", and then converted to 0
console.log(12 > []); // true, since {}.toString() is "", and then converted to 0
console.log("[a" < []); // false, since {}.toString() is ""
console.log("[a" > []); // true, since {}.toString() is ""
console.log('-- 6. According to 4 and 5, we can get below weird result: --');
console.log(null < []); // false
console.log(null > []); // false
console.log(null == []); // false
console.log(null <= []); // true
console.log(null >= []); // true
似乎没有人谈论原因 (arr && arr == false)为真。只是为了不确定运算符优先级的人,根据MDN, ==的优先级高于&&,所以它实际上是(arr && (arr == false))。在通配符的答案之后,它是真&&真,所以它是真。
Var arr = []; 如果(arr & & arr = = false) console.log(“……什么? ?”);
当我尝试使用knockout.js映射插件时,上述方法都没有帮助我,也许是因为“空数组”并不是真的空。
我最终使用:data-bind="if: arr()。长度”,这就成功了。
这是专门针对knockout的,不是OP的问题,但也许它会帮助其他在类似情况下浏览这里的人。
有元素的数组(无论是否为0、false或另一个空数组)总是使用抽象等式比较==解析为true。
1. [] == false; // true, because an empty array has nothing to be truthy about
2. [2] == false; // false because it has at least 1 item
3. [false] == false; // also false because false is still an item
4. [[]] == false; // false, empty array is still an item
但是使用严格相等比较===,你试图计算变量的内容以及它的数据类型,这就是为什么:
1. [] === false; // false, because an array (regardless of empty or not) is not strictly comparable to boolean `false`
2. [] === true; // false, same as above, cannot strictly compare [] to boolean `true`
3. [[]] === false; // true, because see #1