instanceof和typeof
instanceof
在 JavaScript 中,instanceof 运算符用于检测一个对象是否是特定构造函数的实例。它的语法如下:
1 | object instanceof constructor |
- object:需要检测的对象。
- constructor:构造函数。
如果object是constructor的实例,则返回true;否则返回false。
工作原理
instanceof 运算符通过检查对象的原型链来确定该对象是否是某个构造函数的实例。具体来说,它会检查对象的原型链中是否包含构造函数的 prototype 属性所引用的对象。
示例
示例 1:基本用法
1 | function Person(name) { |
在这个示例中,person1 是通过 Person 构造函数创建的,所以 person1 instanceof Person 返回 true。而 person2 是一个普通的对象,不是通过 Person 构造函数创建的,所以 person2 instanceof Person 返回 false。
示例 2:原型链
1 | function Animal(name) { |
在这个示例中,Dog 构造函数继承了 Animal 构造函数。dog1 是通过 Dog 构造函数创建的,所以 dog1 instanceof Dog 返回 true。因为 Dog 继承了 Animal,所以 dog1 instanceof Animal 也返回 true。所有 JavaScript 对象最终都继承自 Object,所以 dog1 instanceof Object 也返回 true。
常见用途
- 类型检查:确定一个对象是否是某个特定构造函数的实例。
- 继承检测:检查一个对象是否在某个原型链上。
- 多态:在方法中根据对象的类型执行不同的操作。
限制
instanceof 运算符在跨 iframe 或跨窗口(window)的情况下可能会出现问题,因为不同窗口中的构造函数是不同的实例。例如:
1 | const iframe = document.createElement('iframe'); |
在这个示例中,arr 是在 iframe 中创建的 Array 实例,所以 arr instanceof Array 返回 false,因为 Array 在不同的窗口中是不同的构造函数。
替代方案
如果需要在跨窗口的情况下进行类型检查,可以使用 Object.prototype.toString.call(value) 方法:
1 | const arr = new iframeArray(1, 2, 3); |
这个方法会返回一个表示对象类型的字符串,可以用来准确地判断对象的类型,即使在跨窗口的情况下也有效。
总结
instanceof 运算符是一个非常有用的工具,用于检测对象是否是某个构造函数的实例。它通过检查对象的原型链来工作,但在跨窗口的情况下可能会出现问题。在这种情况下,可以使用 Object.prototype.toString.call(value) 作为替代方案。
🎈instanceof 可以检测直接量吗
在 JavaScript 中,instanceof 运算符主要用于检测一个对象是否是特定构造函数的实例。对于基本数据类型的直接量(如数字、字符串、布尔值等),instanceof 运算符通常不会返回有意义的结果,因为这些直接量不是通过构造函数创建的。
基本数据类型的直接量
基本数据类型的直接量包括数字、字符串、布尔值、null、undefined、Symbol 和 BigInt。这些直接量不是对象,因此不具有原型链,instanceof 运算符对它们无效。
1 | console.log(5 instanceof Number); // false |
包装对象
虽然基本数据类型的直接量不是对象,但 JavaScript 提供了包装对象(如 Number、String、Boolean),可以将基本数据类型转换为对象。对于这些包装对象,instanceof 运算符可以返回 true。
1 | console.log(new Number(5) instanceof Number); // true |
特殊情况:null 和 undefined
null 和 undefined 是特殊的值,它们不是任何构造函数的实例,因此 instanceof 运算符对它们总是返回 false。
1 | console.log(null instanceof Object); // false |
总结
- 基本数据类型的直接量:
instanceof运算符对它们无效,总是返回false。 - 包装对象:可以使用
instanceof运算符检测包装对象是否是特定构造函数的实例。 null和undefined:instanceof运算符对它们总是返回false。
如果你需要检测一个值是否是基本数据类型,可以使用typeof运算符,它返回一个表示值的类型的字符串。
1 | console.log(typeof 5); // "number" |
通过 typeof 运算符,你可以准确地检测一个值是否是基本数据类型。
💎instanceof 语句 (书)
instanceof 语句比 typeof 语句更进了一步,可以判断一个对象是不是某种类型的实例。 就好像周围的东西可以分为动物、植物、空气、水、金属等大的类型,而动物、植物以及金属还可以再进行更细的分类 。 可 peof 的作用就是查 看一样东西属于 什么大的 类型,例 如 是动 物还是植物,而 instanceof 可以判断东西的具体类型,例如,如果是动物的话,可以判断是不是人,如果是人还可以判断是黄种人还是白种人 、黑种人等。 instanceof 语句的结构如下。
1 | obj instanceof TypeObject |
instanceof 语句的返回值为布尔类型,表示判断是否正确。例如,下面的例子使用 instanceof 来判断 m 变量是否为数组类型。
1 | var arr = [1, 2 , 3]; |
02 function类型对象 会介绍 function 类型的对象,可以使用 new 关键字来创建 object 类型的对象,那时就可以使用 instanceof 来判断一个变量是否为指定类型的 function 对象创建的。
在 JavaScript 中,instanceof 运算符用于检测一个对象是否是特定构造函数的实例。它返回一个布尔值,表示对象是否在构造函数的原型链上。以下是关于 instanceof 语句的详细解释:
语法
1 | object instanceof constructor |
object:要检测的对象。constructor:构造函数。
示例
基本用法
1 | function Person(name) { |
检测内置对象类型
1 | let arr = [1, 2, 3]; |
工作原理
instanceof 运算符的工作原理是检查对象的原型链是否包含构造函数的 prototype 属性所引用的原型对象。具体步骤如下:
4. 获取构造函数的 prototype 属性。
5. 检查对象的原型链是否包含该原型对象。
6. 如果包含,返回 true;否则,返回 false。
示例
1 | function Person(name) { |
注意事项
- 原型链的影响
- 如果对象的原型链被修改,
instanceof的结果可能会受到影响。 - 例如:
1
2
3
4
5
6
7function Person(name) {
this.name = name;
}
let person1 = new Person("John");
// 修改原型链
person1.__proto__ = {};
console.log(person1 instanceof Person); // false
- 如果对象的原型链被修改,
- 跨iframe或window的情况
- 在不同的 iframe 或 window 中,即使构造函数相同,
instanceof也可能返回false,因为每个 iframe 或 window 都有自己的全局对象和原型链。 - 例如:
1
2
3
4
5
6
7
8
9
10
11
12// 在主页面中
function Person(name) {
this.name = name;
}
// 在 iframe 中
let iframe = document.createElement('iframe');
document.body.appendChild(iframe);
let iframeContent = iframe.contentWindow;
let person1 = new Person("John");
let person2 = new iframeContent.Person("Jane");
console.log(person1 instanceof Person); // true
console.log(person2 instanceof Person); // false
- 在不同的 iframe 或 window 中,即使构造函数相同,
- 检测 null 和 undefined
null和undefined没有原型链,因此instanceof会返回false。- 例如:
1
2console.log(null instanceof Object); // false
console.log(undefined instanceof Object); // false
总结
instanceof用于检测一个对象是否是特定构造函数的实例。- 它通过检查对象的原型链是否包含构造函数的
prototype属性所引用的原型对象来工作。 - 原型链的修改和跨 iframe 或 window 的情况会影响
instanceof的结果。 null和undefined没有原型链,因此instanceof会返回false。
理解instanceof的这些特性可以帮助你更准确地检测对象的类型和来源。
💎typeof 语句
typeof 语句的作用是获取变量的类型,调用语法如下 。
typeof 在 ES2015 中的返回值一共有 7 种: undefined 、 function 、 object 、 boolean 、 number 、 string 和 symbol ,请看下面的例子。es2020 新增bigint
- typeof
- number
- Number
- NaN
- string
- string
- object
- Object
- null
- Array
- function
- Function
- undefined
- Undefined
- boolean
- Boolean
- symbol
- Symbol
- bigint
- Bigint
- number
需要特别注意的是 ,null 和数组的类型都是 object ,因为 null 本身也是一个对象,而数组中可以包含其他任何类型的元素,它并不是底层对象,所以它们没有自己独有的类型 。
undefined 是一种特殊的类型,它所代表的是这么一种类型:它们有名字,但是不知道自己是什么类型。即只要有名字但是没有赋值的变量都是 undefined 类型。如果用之前学习过的内存模型来说, undefined 类型的对象就是只占用一块内存空间(用来保存变量名字)的对象。
另外, symbol 类型是 ES2015 中新增的内容,可以查看 Symbol
。
instanceof 和 typeof 有什么区别?
instanceof 和 typeof 是 JavaScript 中用于检测变量类型的两种不同的运算符,它们在功能和用途上有显著的区别。以下是对这两个运算符的详细对比:
1. typeof 运算符
- 用途
typeof用于检测变量的基本数据类型。它返回一个字符串,表示变量的类型。
- 返回值
typeof返回的字符串有以下几种:"undefined":变量未定义"boolean":布尔值"number":数字"string":字符串"symbol":符号(ES6 新增)"bigint":大整数(ES2020 新增)"object":对象、数组、null"function":函数
- 示例
1
2
3
4
5
6
7
8
9
10console.log(typeof undefined); // "undefined"
console.log(typeof true); // "boolean"
console.log(typeof 42); // "number"
console.log(typeof "Hello"); // "string"
console.log(typeof Symbol()); // "symbol"
console.log(typeof BigInt(1)); // "bigint"
console.log(typeof {}); // "object"
console.log(typeof []); // "object"
console.log(typeof null); // "object"(这是一个历史遗留问题)
console.log(typeof function() {}); // "function"
2. instanceof 运算符
- 用途
instanceof用于检测一个对象是否是特定构造函数的实例。它返回一个布尔值,表示对象是否在构造函数的原型链上。
- 返回值
instanceof返回true或false。
- 示例
1
2
3
4
5
6
7
8
9
10
11function Person(name) {
this.name = name;
}
let person1 = new Person("John");
let person2 = { name: "Jane" };
console.log(person1 instanceof Person); // true
console.log(person2 instanceof Person); // false
console.log(person1 instanceof Object); // true
console.log([] instanceof Array); // true
console.log([] instanceof Object); // true
console.log({} instanceof Object); // true
3. 主要区别
- 检测对象类型
typeof用于检测基本数据类型,返回字符串。instanceof用于检测对象是否是特定构造函数的实例,返回布尔值。
- 对
null和undefined的处理typeof null返回"object",这是一个历史遗留问题。typeof undefined返回"undefined"。null和undefined没有原型链,因此instanceof会返回false。
- 跨 iframe 或 window 的情况
typeof不受跨 iframe 或 window 的影响。instanceof在不同的 iframe 或 window 中,即使构造函数相同,也可能返回false,因为每个 iframe 或 window 都有自己的全局对象和原型链。
- 检测数组和对象
typeof对数组和对象都返回"object"。instanceof可以区分数组和对象,[] instanceof Array返回true,{} instanceof Object返回true。
4. 总结
typeof:用于检测基本数据类型,返回字符串。对null和undefined有特殊处理,对数组和对象都返回"object"。instanceof:用于检测对象是否是特定构造函数的实例,返回布尔值。对null和undefined返回false,可以区分数组和对象,受跨 iframe 或 window 的影响。
5. 实际应用
- 检测基本数据类型
- 使用
typeof。 - 例如:
1
2
3if (typeof value === "string") {
// 处理字符串
}
- 使用
- 检测对象类型
- 使用
instanceof。 - 例如:
1
2
3if (value instanceof Array) {
// 处理数组
}
- 使用
- 综合检测
- 有时需要结合使用
typeof和instanceof。 - 例如:理解
1
2
3if (typeof value === "object" && value !== null && value instanceof Array) {
// 处理非 null 对象且是数组
}typeof和instanceof的区别和用途,可以帮助你更准确地进行类型检测和对象管理。
- 有时需要结合使用