前言
常见的判断数据类型的方法主要有typeof,instanceof,但这两种方法都有缺陷。
typeof :
object,arr,null不能分辨,都返回object
instanceof :
Number,Boolean,String基本数据类型不能判断,都返回false
undefined,null无原型链,不能使用instanceof
最精准的方法为Object.prototype.toString.call(),但不易识记,因此本文主要介绍其原理,辅助理解记忆。
Object.prototype.toString.call()原理
- 首先
Object.prototype有一个内置方法为toString,其返回格式为[object xxxx],其中xxxx表示调用这个方法的数据的数据类型.
const JudgeType = Object.prototype.toString
console.log(JudgeType.call(1),'数字') //[object Number] 数字
console.log(JudgeType.call('字符串'),'字符串') //[object String] 字符串
console.log(JudgeType.call(true),'布尔') //[object Boolean] 布尔
console.log(JudgeType.call(undefined),undefined) //[object Undefined] undefined
console.log(JudgeType.call(null),null) //[object Null] null
console.log(JudgeType.call([]),'数组') //[object Array] 数组
console.log(JudgeType.call({}),'对象') //[object Object] 对象
console.log(JudgeType.call(function(){}),'函数') //[object Function] 函数
//ES6新增
console.log(JudgeType.call(Symbol()),'symbol') //[object Symbol] symbol
console.log(JudgeType.call( new Set()),'set') //[object Set] set
console.log(JudgeType.call( new Map()),'map') //[object Map] map
- 同时,js内部重写了一些数据类型的
toString的方法,例如Function.toString(),其返回值为该函数的字符串格式.
const test = function(){
console.log(111)
}
console.log(test.toString()); //"function(){console.log(111)}"
-
因此,如果我们直接使用这些数据类型的
toString方法时,根据原型链的原理会寻找最近一级拥有toString方法的原型对象,这样会直接寻找到其构造函数的原型对象上的toString方法,而无法使用Object.prototype的toString方法. -
想要使用
Object.prototype.toString有两种方法(以函数为例):
1.删除该数据类型的构造函数的原型对象上的toString方法
delete Function.prototype.toString
2.改变Object.prototype.toString的this指向
Object.prototype.toString.call(function(){})
显然方法1我们并不常用,因此可以采用方法2,即使用call直接将this指向改为需要判断的数据
尾声
如果发现本文有错误,还请在评论区指正;如果看官觉得本文对你有帮助,麻烦点一个小小的赞