细说javascript typeof操作符

typeof定义

typeof是一元运算符,用来返回操作数类型的字符串。下面是ECAMScript5.1关于typeof的标准定义:

NOTE:上面表格标红处应为“object”。

typeof疑惑

Value               Class      Type
-------------------------------------
null null object
"foo" String string
new String("foo") String object
1.2 Number number
new Number(1.2) Number object
true Boolean boolean
new Boolean(true) Boolean object
new Date() Date object
new Error() Error object
[1,2,3] Array object
new Array(1, 2, 3) Array object
new Function("") Function function
/abc/g RegExp object
new RegExp("meow") RegExp object
{} Object object
new Object() Object object

NOTE:上面表格中,Class 一列表示对象的内部属性 [[Class]] 的值,Type 一列表示 typeof 操作符的运算结果。

仔细观察上面的javascript类型表格,聪明的你也许已经发现了问题所在:type列大多数情况下都返回 "object"并且和class列的值不一致。因此可以说typeof运算符可以用来获取操作数类型,但很可能得不到想要的结果,所以不应该用typeof来检测对象的类型。说的这里你可能会有疑惑了,typeof不能用来检测对象类型那用来干嘛,到底该怎么检测对象的类型?

别着急,先来看看对象的[[Class]]这个内部属性:

对于object的内部属性[[Class]],ECMAScript5.1是这么说的:ECAMScript规范每种内置对象都定义了 [[Class]] 内部属性。宿主对象的 [[Class]] 内部属性的值可以是"Arguments", "Array", "Boolean", "Date", "Error", "Function", "JSON", "Math", "Number", "Object", "RegExp", "String" 的任何字符串。[[Class]] 内部属性的值用于内部区分对象的种类。

NOTE:规范中除了通过 Object.prototype.toString ( ) 没有提供任何手段使程序访问此值。

明白了,原来可以通过 Object.prototype 上的toString()方法获取[[Class]]属性,[[Class]]属性就是对象的真正类型,那我们就来看看Object.prototype.toString ( ) 是何方圣神:

是不是有点豁然开朗的感觉,于是很快写出以下代码:

/**
* _typeof() returns type of obj
*
* @obj 要检测的对象
*/
function _typeof(obj) { // Object.prototype.toString 返回一种标准格式字符串("[object ", class, and "]"),
// 所以通过 slice 截取指定位置的字符串
return Object.prototype.toString.call(obj).slice(8, -1);
} //测试结果
>_typrof([])
‘Array’ >_typrof(null)
‘null’ >typrof new abc/g
‘RegExp’

到这里大家也许会想不过如此,如果你真的这么认为,只能对你说句Too young Too simple,请往下看:

// IE678
Object.prototype.toString.call(null) // "[object Object]"
Object.prototype.toString.call(undefined) // "[object Object]"

那么到底如何正确的判断javascript的数据类型又做到浏览器的兼容呢,聪明的你应该已经想到了jquery,来看看jQuery.type()是怎样实现的:

var class2type = {};

"Boolean Number String Function Array Date RegExp Object Error".split(" ").forEach(function (e, i) {
class2type["[object " + e + "]"] = e.toLowerCase();
}); //当然为了兼容IE低版本,forEach需要一个polyfill,不作细谈了。
function _typeof(obj) { if (obj == null) {
return String(obj);
} return typeof obj === "object" || typeof obj === "function" ?
class2type[class2type.toString.call(obj)] || "object" : typeof obj;
} // IE678
>_typrof(null)
‘null’ >_typrof(undefined)
‘undefined

关于数据类型的判断到这里就告一段落了,既然typeof不能用作数据类型的判断,那typeof可以应用在哪方面呢,往下看。

typeof用途

  1.检测变量是否定义或是否赋值 

Typeof会在两种情况下返回‘undefined’::一个变量没有被声明的时候,和一个变量的值是undefined的时候。

    > typeof undeclaredVariable

   'undefined'

   > var declaredVariable;

   > typeof declaredVariable

'undefined'

  2.区分对象值和原始值
function isObject(obj) {
var type = typeof obj; //typeof把函数和对象看成是不同的类型,而且typeof null返回"object"
return (type === 'function' || (type === 'object' && !!Obj));
}
  3.某个值是否是函数
function isFunction(obj) {

    //这样做是会出现兼容性的问题(IE 11, Safari 8),有兴趣的朋友可以去了解
return typeof obj === 'function';
}

总结

通过本文我们了解到,检测一个对象的类型尽量使用Object.prototype.toString()方法,以及如何做到个浏览器的兼容性。关于typeof操作符,虽然列举了几个典型的应用场景,不过建议除非为了检测一个变量是否已经定义,尽量避免使用typeof操作符。

参考

http://es5.github.io/

http://lzw.me/pages/ecmascript/

http://bonsaiden.github.io/JavaScript-Garden/zh/

细说javascript typeof操作符的更多相关文章

  1. javaScript数据类型与typeof操作符

    1,typeof操作符. typeof操作符是用来检测变量的数据类型.使用:typeof  变量名;返回以下字符串: 字符串 描述 undefined 未定义 boolean 布尔值 string 字 ...

  2. JavaScript中的typeof操作符用法实例

    在Web前端开发中,我们经常需要判断变量的数据类型.鉴于ECMAScript是松散类型的,因此需要有一种手段来检测给定变量的数据类型——typeof就是负责提供这方便信息的操作符.   对一个值使用t ...

  3. typeof操作符和instanceof操作符的区别 标签: JavaScript 2016-08-01 14:21 113人阅读 评论(

    typeof主要用于检测变量是不是基本数据类型 typeof操作符是确定一个变量是字符串.数值.布尔类型,还是undefined的最佳工具.此外,使用typeof操作符检测函数时,会返回"f ...

  4. JavaScript类型检测, typeof操作符与constructor属性的异同

    *#type.js function Person(name, age) { this.name = name; this.age = age; } var d = {an: 'object'}; v ...

  5. JavaScript typeof, null, 和 undefined

    typeof 操作符 你可以使用 typeof 操作符来检测变量的数据类型. 实例 typeof "John"                // 返回 string typeof ...

  6. javascript typeof 和 instanceof 的区别和联系

      这篇文章是我看完<JavaScript高级程序设计(第2版)>书籍的随笔文章,目的只有一个,以备自己和网友们方便参考和记忆! typeof是什么?       typeof 是一个操作 ...

  7. 细说JavaScript对象(1):对象的使用和属性

    JavaScript 中的一切都可以视为对象,除了两个特例:null 和 undefined. false.toString(); // 'false' [1, 2, 3].toString(); / ...

  8. typeof操作符返回一个字符串,表示未经计算的操作数的类型。

    typeof操作符返回一个字符串,表示未经计算的操作数的类型.   语法 typeof运算符后跟操作数: typeof operand or typeof (operand) 参数 operand 是 ...

  9. typeof操作符,返回数据类型Array.isArray()、Object.prototype.toString.call()

    源地址https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Operators/typeof typeof操作符 // N ...

随机推荐

  1. Rikka with Mista 线段树求交点个数

    由于上下线段是不可能有交点的 可以先看左右线段树,按照y递增的顺序,对点进行排序. 升序构造,那么对于从某一点往下的射线,对于L,R进行区间覆盖,线段交点个数就是单点的被覆盖的次数. 降序构造,那么对 ...

  2. Logback新版本报no applicable action for [Encoding]问题

    logback.xml配置文件如下: <?xml version="1.0" encoding="UTF-8"?> <configuratio ...

  3. Element-ui学习笔记3--Form表单(二)

    Input输入框 Input 为受控组件,它总会显示 Vue 绑定值. 通常情况下,应当处理 input 事件,并更新组件的绑定值(或使用v-model).否则,输入框内显示的值将不会改变. 不支持  ...

  4. 什么是响应式设计?响应式设计的基本原理是什么?如何兼容低版本的 IE?

    响应式网站设计(Responsive Web design)的理念是:集中创建页面的图片排版大小,可以智能地根据用户行为以及 使用的设备环境(系统平台.屏幕尺寸.屏幕定向等)进行相对应的布局,无论用户 ...

  5. 第三次脱发——Scurm学(ctrl)习(C)心得

    Scrum 学习心得: 首先,敏捷并不是一门具体的技术,而是一种理念或者说是一种思想.它可以指导我们更加高效的开发. 其次,敏捷开发都具有以下共同的特征: 迭代式开发 增量交付 开发团队和用户反馈推动 ...

  6. 深入Java线程管理(三):线程同步

    一. 引入同步: 有一个很经典的案例,即银行取款问题.我们可以先看下银行取款的基本流程: 1)用户输入账户.密码,系统判断用户的账户.密码是否匹配. 2)用户输入取款金额. 3)系统判断账户金额是否大 ...

  7. [转]Node.js中package.json中^和~的区别

    webpack 项目的package.json 文件列出了项目所依赖的插件和库,同时也给出了对应的版本说明,但是在版本说明前面还有个符号:'^'(插入符号)和'~'(波浪符号),总结了下他们之间的区别 ...

  8. Python--day61--Django项目配置相关

    static文件查找:

  9. P1038 间谍入侵

    题目描述 爱丽丝魔法王国成立10周年,于是决定矩形国庆大阅兵. 在国庆大阅兵期间,为了防止暗黑王国的间谍乔装成平民混入,需要对每一个进城的人做检测. 因为暗黑王国的人长得和爱丽丝魔法王国的人长得很像, ...

  10. Github上的英文解释

    1.AFAIK: As far as I know.  据我所知 2.SPOF: Single point of failure. 单节点崩溃 3.ASAP: As soon as possible. ...