本文已参与「新人创作礼」活动,一起开启掘金创作之路。
1、instanceof
格式:value instanceof Object
使用这个关键字可以判断数据是否属于某个类型,返回true或false
例如:
let a = 10;
let a2=new Number(10);
let obj = {
name: 'zf',
age: 38
}
let b = null;
let d = undefined;
let namearr = ['asd', 'qew', 'asrt', 'kanzo'];
console.log('========instanceof=============')
console.log(a instanceof Number) //false
console.log(a2 instanceof Number) //true
console.log(Object instanceof Object) //true
console.log(b instanceof Object) //false
console.log(b instanceof Null) //Uncaught ReferenceError: Null is not defined
console.log(d instanceof undefined) //Uncaught TypeError: Right-hand side of 'instanceof' is not an object
console.log(namearr instanceof Object) //true
console.log(namearr instanceof Array) //true
用这个方法检测数据类型是不可靠的。
①无法检测出值为null、undefined的变量。
②在检测引用数据类型时也会产生歧义。诚然Array是派生自Object,它既是对象也是数组,但为了消除歧义使得在判断时,需要做更多的工作。(如function、regExp、argument等类型)
③只能检测出显式装箱的基本数据类型。
此外,要使用instanceof判断一个类型未知的数据,需遍历很多数据类型尝试是否有一个为true,这显然也不是一个聪明的办法。
2、typeof
格式: typeof value
使用这个关键字可以返回数据的数据类型
let a = 10;
let a2 = new Number(10);
let obj = {
name: 'zf',
age: 38
}
let b = null;
let d = undefined;
let namearr = ['asd', 'qew', 'asrt', 'kanzo'];
console.log('========typeof================')
console.log(typeof a) //number
console.log(typeof a2) //object
console.log(typeof obj) //object
console.log(typeof b) //object
console.log(typeof d) //undefined
console.log(typeof namearr) //object
emmm,已经有很大进步了,至少typeof直接把可能正确的数据类型返回给了我们,这比用instanceof一个一个试更加容易,但它依旧不可靠。
①检测null类型,错误的返回了object。这是JavaScript创立时遗留的历史问题,有更好的方法解决它。
②将基本类型对应的显式装箱,返回成了对象。与Array相同,虽然没错,但不是我们想要的。
3、Object.prototype.toString.call(TargetObject)
首先要将Object.prototype.toString方法与其他类型的toString方法区分开来。
toString最初是Object原型的方法,但Array、Function、Arguments等对象作为Object的实例,都对toString函数进行了重写。
以数组为例子,Object.prototype.toString和Array.toString是两个不同的函数。
Object.prototype.toString方法可以得到对象的具体类型
Array.toString方法则是将数组转换成字符串
let a = 10;
let a2 = new Number(10);
let obj = {
name: 'zf',
age: 38
}
let b = null;
let d = undefined;
let namearr = ['asd', 'qew', 'asrt', 'kanzo'];
console.log('========Object.prototype.toString=============')
console.log(Object.prototype.toString.call(a)) //[object Number]
console.log(Object.prototype.toString.call(a2)) //[object Number]
console.log(Object.prototype.toString.call(obj)) //[object Object]
console.log(Object.prototype.toString.call(b)) //[object Null]
console.log(Object.prototype.toString.call(d)) //[object Undefined]
console.log(Object.prototype.toString.call(namearr)) //[object Array]
console.log(namearr.toString()) //asd,qew,asrt,kanzo
Object.prototype.toString.call(target)会以字符串的形式返回target的数据类型。
Object.prototype.toString方法几乎是一个完美的解决方案了,装箱和未装箱的基本类型、null、undefined数据类型都能正确给出。
题外话:Object.prototype身上还有很多好用的函数,用call借调Object.prototype身上函数的情况是会经常遇到的。
4、封装函数myTypeof()
如果对[object Number]的输出格式不太满意,我们可以对Object.prototype.toString方法进行函数封装,根据自己的需求加入一些功能,比如得到一个更满意的数据类型输出格式。
let a = 10;
let myTypeof = function (target) {
let type = Object.prototype.toString.call(target).match(/\[object (\w+)\]/);
return type ? type[1] : '';
}
console.log(myTypeof(a)) //Number