instanceof 本质是检测对象原型链是否包含指定构造函数的 prototype。它沿原型链查找,支持手动设置原型、跨 iframe 使用,并可通过 symbol.hasinstance 自定义行为,但左侧操作数需为对象,否则可能报错。

instanceof 不只是判断“是不是某个构造函数的实例”,它本质是检测对象的原型链上是否存在指定构造函数的 prototype 对象。
原理:沿着原型链向上查找
表达式 a instanceof B 的执行过程是:
- 获取
B.prototype(注意:是构造函数的prototype属性,不是实例的) - 从
a的[[Prototype]](即__proto__)开始,逐级向上查找 - 只要某一级等于
B.prototype,就返回true;查到顶层(null)还没找到,返回false
这意味着即使对象不是用 new B() 创建的,只要它的原型链被手动设置过,也能通过检测。比如:
const obj = {};
Object.setPrototypeOf(obj, Array.prototype);
console.log(obj instanceof Array); // true
可跨执行上下文使用(如 iframe)
与 constructor 或 Object.prototype.toString 不同,instanceof 在 iframe 中依然可靠,因为它依赖的是原型链结构,而非具体构造函数引用。
- 在父页面创建的数组传入 iframe,
arr instanceof Array仍为true - 因为 iframe 中的
Array.prototype和父页面的Array.prototype是同一个对象(共享) - 但注意:自定义构造函数若未显式暴露,跨 iframe 就无法直接用
instanceof检测
配合 Symbol.hasInstance 实现自定义行为
ES6 允许构造函数定义静态方法 [Symbol.hasInstance](instance),从而接管 instanceof 的判断逻辑。
- 当执行
obj instanceof C时,引擎会优先调用C[Symbol.hasInstance](obj) - 可用于模拟接口、类型伪装或兼容旧代码
class EvenNumber {
static [Symbol.hasInstance](obj) {
return Number.isInteger(obj) && obj % 2 === 0;
}
}
console.log(42 instanceof EvenNumber); // true
console.log(43 instanceof EvenNumber); // false
注意 null 和 undefined 的边界情况
instanceof 左侧操作数必须是对象,否则直接报错(TypeError)。
-
null instanceof Object→false(null原型链为空,不报错) -
undefined instanceof Object→ 报错(undefined不是对象) -
123 instanceof Number→false(原始值没有原型链,自动装箱发生在运算前,但装箱后的临时对象不保留)
安全做法:先用 typeof 或 Object(value) !== value 排除非对象值。











