nac*_*son 8 javascript collections dictionary set ecmascript-6
我只是想检查的对象是Map或Set,而不是一个Array.
检查我正在使用lodash的数组_.isArray.
function myFunc(arg) {
if (_.isArray(arg)) {
// doSomethingWithArray(arg)
}
if (isMap(arg)) {
// doSomethingWithMap(arg)
}
if (isSet(arg)) {
// doSomethingWithSet(arg)
}
}
Run Code Online (Sandbox Code Playgroud)
如果我要实现isMap/ isSet,它需要看起来像什么?我希望它能够捕获Map/的子类,Set如果可能的话.
Ber*_*rgi 18
这种情况类似于ES5之前的方法,可以正确可靠地检测数组.请参阅这篇伟大的文章,了解可能存在的实施缺陷isArray.
我们可以用
obj.constructor == Map/ Set,但这对子类实例不起作用(很容易被欺骗)obj instanceof Map/ Set,但这仍然不能跨越领域(可以被原型修改欺骗)obj[Symbol.toStringTag] == "Map"/ "Set",但这可以琐碎地再次被欺骗.要确定,我们需要测试对象是否有[[MapData]]/ [[SetData]]内部插槽.哪个不容易获取 - 它是内部的.我们可以使用黑客攻击:
function isMap(o) {
try {
Map.prototype.has.call(o); // throws if o is not an object or has no [[MapData]]
return true;
} catch(e) {
return false;
}
}
function isSet(o) {
try {
Set.prototype.has.call(o); // throws if o is not an object or has no [[SetData]]
return true;
} catch(e) {
return false;
}
}
Run Code Online (Sandbox Code Playgroud)
对于常见用途,我建议instanceof- 它简单,易懂,高效,适用于大多数合理的情况.或者你马上去打鸭子,只检查对象是否有has/ get/ set/ delete/ add/ delete方法.
您可以使用instanceof运算符:
function isSet(candidate) {
return candidate instanceof Set;
}
Run Code Online (Sandbox Code Playgroud)
如果候选对象Set.prototype在其原型链中,则instanceof运算符返回true。
编辑- 虽然这instanceof件事在大多数情况下都会起作用,但在某些情况下它不会起作用,如 Bergi 的回答中所述。
| 归档时间: |
|
| 查看次数: |
1259 次 |
| 最近记录: |