数组中的'undefined'元素的JavaScript'in'运算符
请考虑下面的代码片段:
> a = [1, undefined, undefined, undefined, 3] [1, undefined, undefined, undefined, 3] > b = [1,,,,3] [1, undefined × 3, 3] > 1 in a true > 1 in b false
我错过了什么吗? 这似乎是,根据我如何定义数组中undefined
元素, in
运算符的行为有所不同。
数组只是正常的JavaScript对象,有一些专业化。 从ECMA 5.1规范的“数组对象”部分引用
数组对象对特定类的属性名称给予特殊的处理。 当且仅当ToString(ToUint32(P))等于P且ToUint32(P)不等于2 32 -1时,属性名称P(以String值forms)才是数组索引 。
所以, 数组索引只是数组对象的属性 。 现在,让我们看看数组中缺less的元素。
从ECMA 5.1标准规范引用,
数组元素可能在元素列表的开始,中间或结束时被忽略。 只要元素列表中的逗号前面没有AssignmentExpression(即逗号在开头或逗号之后),缺less的数组元素将有助于数组的长度,并增加后续元素的索引。 数组元素没有被定义。 如果元素在数组末尾被消除,那么该元素不会影响数组的长度。
所以,当你说
b = [1,,,,3];
除了元素1和3之外,其他所有元素都被视为数组中的缺失元素。 现在元素1
和3
对应于属性0
和4
(在JavaScript中数组索引以0
开头)。
你可以这样检查
console.log(Object.getOwnPropertyNames(b)); # [ '0', '4', 'length' ] console.log(Object.getOwnPropertyNames(a)); # [ '0', '1', '2', '3', '4', 'length' ]
只有指数0
和4
在b
。 您可能想知道为什么a
具有从0
到4
的属性,但值是undefined
。 因为指数1,2和3的元素被定义为undefined
,在b
,我们不知道这些值是什么。 这就是为什么他们没有分配到一个财产(索引)。
现在,你正在检查1
是否在b
, in
运算符中。 in
运营商MDN Doc中引用,
如果指定的属性在指定的对象中,则in运算符返回true。
所以,你基本上是检查1
是否是b
的属性之一,不是。 这就是为什么b
'1'
返回false
。
注意:
如果你想知道1
是否在数组中,你应该使用Array.prototype.indexOf
,像这样
console.log(a.indexOf(1)); # 0 console.log(b.indexOf(1)); # 0 console.log(b.indexOf(5)); # -1
Array.prototype.indexOf
返回-1
如果被search的元素不在数组中。 所以,你可能想要做这样的事情
console.log(a.indexOf(1) !== -1); # true console.log(b.indexOf(1) !== -1); # true console.log(a.indexOf(5) !== -1); # false
在你的例子中,a [1]被定义,但是被设置为undefined
,因此1 in a == true
。 相反,b [1]完全没有设置,因此1 in b == false
。 这就是为什么有些人说undefined
很奇怪。
要检查数组a
是否具有值 1,请使用a.indexOf(1) != -1
。
为了检查a[1]
是否被定义,使用a.hasOwnProperty("1")
( 1 in a
是微妙不同的,可能实际上并不是你想要的,因为如果1
被定义在a
原型而不是在a
本身)。
要将a[1]
设置为undefined
,请使用a[1] = undefined
。
要定义a[1]
停止,请使用delete a[1]
。
//-1 means not in the list //['a','b','c'].indexOf('a') is return index if not find in the list then it give -1. if(['a','b','c'].indexOf('d') == -1) { console.log('yes it -1') }