上周写了一篇文章 常见工具方法的编写——逐步实现 once 方法 - ,然而不知道为什么一周过去了并没有什么阅读量,综合分析了一下,觉得应该是发布时间的问题,果然不能在白天发布,以后还是回到晚上十点以后发布吧!为了提升上一篇的阅读量,在本篇开始之前,不付广告费地打个广告,感兴趣的小伙伴可以直接点击上面的链接查看哦!
下面进入正题,本篇又回到了《前端面试题》系列,这次来探讨一下 js 中的基本数据类型的检测方式
javascript 中的基本数据类型:Number String Boolean Array Object Null Undefined
常用检测方法 —— typeof
基本使用
var a = ''
typeof a
typeof 并不是一个方法,所以不需要通过()
进行调用,只需要在它的后面紧跟我们需要检测的变量就可以,因为它是一个运算符
每种类型对应的 typeof 的值
typeof 1 // 'number'
typeof '' // 'string'
typeof true // 'boolean'
typeof [] // 'object'
typeof {} // 'object'
typeof null // 'object'
typeof undefined // 'undefined'
typeof function(){} // 'function'
上面的代码中,我们会发现:
- typeof 可以用来检测函数
- 当需要被检测的变量是数组、对象和 null 时,返回的结果都是
object
,因为 js 中的数组,本质上还是一个对象,而 null 在 js 中是一个表示为空的特殊的对象
typeof
可以用来检验变量的类型,那么它的返回值又是什么类型呢?
typeof typeof 1 // 'string'
typeof typeof '' // 'string'
typeof typeof true // 'string'
通过上面的代码,我们知道了typeof
的返回值是一个字符串类型
typeof 的不足
既然数组、对象和 null 通过 typeof 的检验返回的都是object
,这也就说明 typeof 并不能够完美的帮助我们区分数组、对象和 null,某些情况下会给我们的工作带来不便
或许我们可以通过封装一个方法来帮助进行更细致的检测,但有没有别的方式呢?
另一种类型检测方式 —— instanceof
instanceof 运算符用来判断一个构造函数的prototype属性所指向的对象是否存在另外一个要检测对象的原型链上
简单来说,就是检测一个对象是否继承于另一个对象
基本使用
var a = 1
a instanceof Number // true
a instanceof String // false
instanceof
前为我们需要检测的变量,后面是需要判断是否有继承关系的对象,返回一个布尔值表示是否存在继承关系
所以聪明的小伙伴肯定想到了下面这种情况:
var a = []
a instanceof Array // true
a instanceof Object // true
var b = {}
b instanceof Array // false
b instance Object // true
var c = null
c instanceof Object // false
因为数组本质上也是一个对象,所以上面的两个计算结果都会返回true
,但是我们也会发现,数组的检测已经和正常形式的对象区分开来了
当一个变量是null
时,判断是否为Object
的实例,返回为false
,说明 null 虽然是个特殊的对象,但是并不继承自 Object
instanceof 的不足
虽然 instanceof
能够区分数组、对象和 null,但是它的右边只能够接收一个对象类型,这也就说明,无法用instanceof
来检测数字、字符串、布尔、Null 和 Undefined 类型
var a = 1
a instanceof Number // false
var b = null
b instanceof Null // Uncaught TypeError: Right-hand side of 'instanceof' is not an object
结合 typeof 与 instanceof
下面的代码是作者结合两者的特点封装过得检测变量类型的方法
function typeOf(item) {
if (arguments.length != 1) throw new Error('must given one argument')
var type = typeof item
// 判断是否为空
if (!item) {
return type === 'number' ? 'number' :
type === 'string' ? 'string' :
type === 'boolean' ? 'boolean' :
type === 'undefined' ? 'undefined' : 'null'
}
// 判断是否为 object
return type !== 'object' ? type :
// 判断是数组还是对象
(item instanceof Array) ? 'array' : 'object'
}
使用上面的方法检验变量类型:
console.log(typeOf(0)) // 'number'
console.log(typeOf(1)) // 'number'
console.log(typeOf('')) // 'string'
console.log(typeOf('sss')) // 'string'
console.log(typeOf(true)) // 'boolean'
console.log(typeOf(false)) // 'boolean'
console.log(typeOf([])) // 'array'
console.log(typeOf({})) // 'object'
console.log(typeOf(null)) // 'null'
console.log(typeOf(undefined)) // 'undefined'
console.log(typeOf(function(){})) // 'function'
最终,我们还是通过封装 typeof 和instanceof 完成了最终我们需要的变量检测方法