typeof和instanceof两者的缺陷与优化 - Web前端
作者:98wpeu发布时间:2026-08-26分类:网页前端技术浏览:7

在javascript中,typeof 和 instanceof 是用来判断数据类型比较通用的两个方法,但这两种方式并不能完全解决实际中遇到的问题。因此,这篇文章的目的是通过对这两个方法介绍来分析其存在的问题和不足,并提供一种比较简单的优化方案。
typeof
typeof 返回一个表达式的数据类型的字符串,返回结果为JavaScript中的基本数据类型,包括:number、boolean、string、Object、undefined、function等6种数据类型。
typeof 100; //numbertypeof (1==1); //booleantypeof ''onepixel''; //Stringtypeof {} ; //objecttypeof onepixel; // undefinedtypeof parseInt; // functiontypeof [];//objecttypeof new date(); //object可以看出,typeof 可以准确的判断除object以外的基础数据类型,但不能区分object类型的具体类型,比如 Array 、Date 以及自定义类。
instanceof
instanceof 本意是用来判断 A 是否为 B 的实例对象,表达式为:A instanceof B,如果A是B的实例,则返回true,否则返回false。 在这里需要特别注意的是:instanceof检测的是原型,那它是怎么检测的呢,我们用一段伪代码来模拟其内部执行过程:
instanceof (A,B) = {var L = A.__proto__;var R = B.prototype;if(L === R) {//A的内部属性__PRoto__指向B的原型对象return true;
}return false;
}从上述过程可以看出,当 A 的 __proto__ 指向 B 的 prototype 时,就认为A就是B的实例对象,我们再来看几个例子:
[] instanceof array; //true{} instanceof Object;//truenew Date() instanceof Date;//truefunction Person(){};new Person() instanceof Person;
[] instanceof Object; //truenew Date() instanceof Object;//truenew Person instanceof Object;//true从上面的例子中,我们发现,虽然 instanceof 能够正确判断 [] 是Array的实例对象,但 instanceof 认为 [] 也是Object的实例对象,为什么呢? 这还需要从JS的原型链说起,我们首先来分析一下[]、Array、Object 三者之间的关系: 从instanceof能够判断出 [].__proto__ 指向 Array.prototype, 而实际上 Array.prototype.__proto__ 指向了Object.prototype,Object.prototype.__proto__ 指向了null,标志着原型链的结束。 因此,[]、Array、Object就形成了一条原型链:

从原型链可以看出,[] 的 __proto__ 最终指向了Object.prototype,因此,js认为 [] 也是Object的实例。当然,类似的new date()、new Person() 也会形成这样一条原型链,因此,用 instanceof 只能够用来判断已知的数据类型,比如:[] instanceof Array , 而不能获取一个对象的具体数据类型。
优化方案
对于这个问题,在阅读JQuery源码时,发现 jQuery 实现了一个较好的解决方案来获取数据类型,由于源码之间存在相互调用不便于阅读和理解,因此,我按照其思路进行了整理和封装,代码如下:
(function(){var class2type = {};var typelist = "Boolean Number String Function Array Date RegExp Object error Symbol".split( " " );
typeList.eachEach(function(item){
class2type[ "[object " + item + "]" ] = item.toLowerCase();
}return {
getObjType:function(obj) {if ( obj == Null ) {return obj + "";
} if(typeof obj === "object" || typeof obj === "function"){return class2type[ toString.call( obj ) ] || "object"}else {return typeof obj;
}
}
}
})()
- 网页前端技术排行
-
- 1[Web前端]用javascript实现默认图片替代未显示的图片 - Web前端
- 2分析Iconfont-阿里巴巴矢量常用图标库 - Web前端
- 3jQuery实例教程:制作网页中可折叠的面板 - Web前端
- 4【第六章】Foundation之按钮和下拉功能 - Web前端
- 5基于jquery的滚动条滚动固定div(附演示下载) - Web前端
- 6jQuery编写widget的一些技巧分享 - Web前端
- 7分享精心挑选的12款优秀jQuery Ajax分页插件和教程 - Web前端
- 8jQuery实现鼠标移到元素上动态提示消息框效果 - Web前端
- 9在Mac/PC上远程调试iPhone/iPad上的网页 - Web前端
- 最近发表
-
- WordPress随机显示特色图片插件:Random Post Thumbnails
- KeePass实现Chrome浏览器自动填充密码方法一
- LNMP一键包nginx 301强制跳转到https教程
- KeePass实现Chrome浏览器自动填充密码方法二
- #建站# 免费的VPS管理软件Xshell8/Xftp8中文版下载
- 使用Xshell 8连接VPS教程_电脑登录vps的方法
- WordPress评论界面添加烟花????效果
- 不同浏览器书签同步方案:坚果云+Floccus_详细使用教程
- iOS端KeePassXC客户端APP:Strongbox Password Safe
- 给WordPress评论中的Gravatar头像图片添加ALT属性


