instanceof
2023年06月15日
一、认识
instanceof
在原型链上查找,查到即是其实例
注意
-
isPrototypeOf()
与instanceof
有什么区别?-
a.isPrototypeOf(b)
: 针对a
本身进行检查 -
b instanceof b
: 针对b.prototype
进行检查
-
二、语法
console.log(1 instanceof Number); // false
console.log("" instanceof String);
console.log(true instanceof Boolean);
console.log({} instanceof Object); // true
console.log([] instanceof Array); // true
console.log(function () {} instanceof Function); // true
三、场景
场景一、实现一个只可以通过new
的方式调用的函数
function Vue() {
if (!(this instanceof Vue)) {
console.log(
"Vue is a constructor and should be called with the `new` keyword"
);
return;
}
console.log("Vue 实例");
}
Vue();
const vue = new Vue();
四、原理 Polyfill
instanceof
通过原型链判断 A instanceof B
, 在A
的原型链中层层查找,是否有原型等于B.prototype
,如果一直找到A
的原型链的顶端(null
;即Object.proptotype.__proto__
),仍然不等于B.prototype
,那么返回false
,否则返回true
。
递归版:
function myInstanceof(obj, constructor) {
if (!(obj && ["object", "function"].includes(typeof obj))) {
return false;
}
let proto = Object.getPrototypeOf(obj);
if (proto === constructor.prototype) {
return true;
} else if (proto === null) {
return false;
} else {
return myInstanceof(proto, targetConstructor);
}
}
function Foo() {}
const foo = new Foo();
console.log(myInstanceof(foo, Foo));
迭代版:
function myInstanceof(obj, constructor) {
if (!(obj && ["object", "function"].includes(typeof obj))) {
return false;
}
let proto = obj;
while ((proto = Object.getPrototypeOf(obj))) {
if (proto === constructor.prototype) {
return true;
} else if (proto === null) {
return false;
}
}
return false;
}
function Foo() {}
const foo = new Foo();
console.log(myInstanceof(foo, Foo));