zoukankan      html  css  js  c++  java
  • JavaScript类型检测汇总

        曾经我以为JavaScript中的类型检测只要使用 typeof instanceof 就可以通通解决。后来我发现我是too young too naive啊!早说过JavaScript是个不严密,有缺陷的语言,通过类型检测才深深地领悟到这一点。接下来我就来剖析下这里面的漏洞及最靠谱的检测方法吧!

    一、typeof运算符

        相信很多同学还跟我曾经以为的一样,typeof操作符只是判断对象类型上不太靠谱,它还是可以用来检测原始值类型的,比如数字、字符串、布尔型。但看了下面的例子你就不这么认为了。

    typeof 'foo'                 //  'string'
    typeof new String('foo')     // 'object'
    
    typeof 2                    // 'number'
    typeof new Number(2)        // 'object'
    
    typeof true                // 'boolean'
    typeof new Boolean(true)   // 'object'

        看出来了么,都是同样的值,如果用构造函数来创建原始值那么用typeof检测的结果就都是’object’!这显然不是我们想要的结果。

    二、instanceof运算符

        那有人说了,typeof沦陷了,我们还有instanceof啊,可是别忘了 instanceof本质上是检测引用类型的原型链的,所以对原始值就根本没有作用。例如:

    'foo' instanceof String     // false
    'foo' instanceof Object     // false
    
    new String('foo') instanceof String   //true
    new String('foo') instanceof Object   //true

        看到了吧,还是不靠谱。

        好吧,让instanceof做不属于它的工作是对它不太公平啦!那让它检测引用类型呢?其实它检测引用类型也有一个严重的限制: 不能跨帧使用。

        假设一个浏览器帧A(frame A)里的一个对象被传入到帧B(frame B)中,两个帧中都定义了Person构造函数,如果来自帧A 的对象是帧A 中Person的实例,则有:

    personA instanceof frameAPerson   //true
    personA instanceof frameBPerson   //false  

        因为每个帧都有Person的拷贝,它被认为是该帧中的Person的拷贝实例,尽管两个定义是一样的。

        同样的问题也出现在其他两个非常重要的内置类型中:数组和函数,所以检测这两个内置类型一般不用instanceof。

        而且instanceof对于对象的整个原型链都能检测到,例如:

    var now = new Date();
    
    now instanceof Date;    //true
    now instanceof Object;  //true

        因此,用instanceof检测某一对象是否属于特定类型并非最佳。

    三、最佳方法

        typof和instanceof已经都被否决了,那么最靠谱的检测方法是什么呢?

        对于JS的内部类型如Number, String, Boolean, Array, Function, Object, RegExp, Date, Error, Math, JSON可以调用Object的内部方法toString, 它可以返回一下格式的信息:’[object ‘+ type + ‘]’,例如:

    Object.prototype.toString.call('foo') === '[object String]';  //true
    Object.prototype.toString.call([1,2,3]) === '[object Array]'; //true

        用这个方法判断以上给出的类型,不管任何浏览器都会返回一样的格式,而且满足跨帧要求。

  • 相关阅读:
    log日志框架和LocationAwareLogger问题
    Eclipse 各种小图标的含义
    自定义log4j日志级别
    在Tomcat配置JNDI数据源的三种方式
    mybatis中"#"和"$"的区别
    Postman用法简介-Http请求模拟工具
    mustache模板技术(转)
    VS的编译选项
    Java Service Wrapper简介与使用
    还活着
  • 原文地址:https://www.cnblogs.com/kongxy/p/4731222.html
Copyright © 2011-2022 走看看