判断数据类型
在JavaScript中,判断数据类型主要有以下几种方式:
1. typeof运算符
javascript
typeof "Hello World"; // "string"
typeof 42; // "number"
typeof true; // "boolean"
typeof undefined; // "undefined"
typeof {a: 1}; // "object"
typeof null; // "object",这是一个历史遗留问题
typeof function(){}; // "function"
- 优点:简单易用,对于基本数据类型(除了
null
)能正确判断其类型。 - 缺点:无法区分引用数据类型,数组、对象和
null
,它们都返回"object"
。
2. instanceof运算符
javascript
[] instanceof Array; // true
{} instanceof Object; // true
function(){} instanceof Function; // true
- 优点:能够判断一个对象是否是其父类型或祖先类型的实例。
- 缺点:只适用于引用数据类型,不能判断基本数据类型。且在有
iframe
的情况下,一个iframe
内的对象类型与另一个iframe
内的同名对象类型不相等。
3. Array.isArray()
javascript
Array.isArray([]); // true
Array.isArray({}); // false
- 优点:直接判断是否为数组,简单明了。
- 缺点:只能用于判断数组。
4. constructor
javascript
(42).constructor === Number; // true
"Hello World".constructor === String; // true
true.constructor === Boolean; // true
[].constructor === Array; // true
{}.constructor === Object; // true
function(){}.constructor === Function; // true
- 优点:直接通过对象的
constructor
属性来判断对象的构造函数,使用简单直观。 - 缺点:
- 如果对象的原型链被修改(例如,如果有人更改了对象的
__proto__
属性或使用了Object.create(null)
创建了一个没有原型的对象),这种方法可能会失效。 - 对于
null
和undefined
,不能直接使用constructor
属性进行判断,因为它们没有constructor
属性,直接访问会抛出错误。
- 如果对象的原型链被修改(例如,如果有人更改了对象的
5. Object.prototype.toString.call()(最优)
javascript
Object.prototype.toString.call("Hello World"); // "[object String]"
Object.prototype.toString.call(42); // "[object Number]"
Object.prototype.toString.call(true); // "[object Boolean]"
Object.prototype.toString.call([]); // "[object Array]"
Object.prototype.toString.call(function(){}); // "[object Function]"
Object.prototype.toString.call(null); // "[object Null]"
Object.prototype.toString.call(undefined); // "[object Undefined]"
- 优点:能够准确判断所有类型的数据,包括基本类型和引用类型。
- 缺点:代码相对冗长,阅读性稍差。