来自 服务器&运维 2019-12-26 01:17 的文章
当前位置: 澳门三合彩票 > 服务器&运维 > 正文

据此代码 3 中 pig 是 Pig 的实例,假设要一口咬住

比如: 复制代码 代码如下: // 代码 1 function Pig() {} var pig = new Pig(); alert; // => true function FlyPig() {} FlyPig.prototype = new Pig(); var flyPig = new FlyPig(); alert(flyPig instanceof Pig); // => true 来看另一段代码: 复制代码 代码如下: // 代码 2 function Pig() { Pig.prototype = {/* some code */} } var pig = new Pig(); alert; // => false 为何上面的猪 pig 不再是猪 Pig 了呢? 当一个对象是某个类的实例时,意味着这个对象具有该类的方法和属性。在 JavaScript 中,一个猪类的特性体现在原型中: 复制代码 代码如下: // 代码 3 function Pig() {} Pig.prototype = { "吃猪食": function() {}, "睡觉": function() {}, "长膘": function() {} }; var pig = new Pig(); alert; //=> true 如果动态改变了猪的特性,让猪变成了牛: 复制代码 代码如下: // 代码 4 Pig.prototype = { "吃草": function() {}, "犁田": function() {} }; var niu= new Pig(); alert; //=> false alert; //=> true 当未改变 Pig 的 prototype 时,猪还是猪,因此代码 3 中 pig 是 Pig 的实例。当改变 prototype 后,猪已经不是猪,而是披着猪皮的牛了。因此代码 4 中 pig 不再是 Pig 的实例,niu 反而是 Pig 的实例。 进一步分析前,先回顾一下 new 的内部机制。代码 2 中的 new Pig() 实际上等价为: 复制代码 代码如下: // var pig = new Pig() 的等价伪代码: var pig = { var o = {}; o.__proto__ = Pig.prototype; // line 2 Pig.call; Pig.prototype = {/* some code */}; // line 4 return o; // line 5 })(); 可以看出,在 line 2 时,o.__proto__ 指向了 Pig.prototype 指向的值。但在 line 4 时,Pig.prototype 指向了新值。也就是说,在 line 5 返回时,pig.__proto__ !== Pig.prototype. 正是这个变化,导致了代码 2 中的 pig 不是 Pig. 已经可以大胆推论出:instanceof 判断 pig 是不是 Pig 的依据是:看隐藏的 pig.__proto__ 属性是否等于 Pig.prototype ! 为了进一步确认,我们可以在 Firefox 下模拟 instanceof 的内部实现代码: 复制代码 代码如下: /** * Gecko 引擎下,模拟 instanceof */ function _instanceof { // instanceof 的左操作数必须是非null对象或函数对象 if((typeof obj !== "object" || obj === null) && typeof obj !== "function") { return false; } // instanceof 的右操作数必须是函数对象 if(typeof cls !== "function") { throw new Error("invalid instanceof operand ; } // 向上回溯判断 var p = obj.__proto__, cp = cls.prototype; while return true; p = p.__proto__; } return false; } 测试页面:simulate-intanceof.html 最后考考大家: 复制代码 代码如下: function Bird() {} var bird = new Bird(); var o = {}; bird.__proto__ = o; Bird.prototype = o; alert; // true or false?

复制代码

ECMA-262 写道

复制代码

那么数组也会被判断为object。

而instaceof是判断对象的类型,比如:

复制代码

var o = { 'name':'lee' };
var a = ['reg','blue'];
 
alert( a instanceof Object );  // true
alert( o instanceof Object );  // true

第一,使用typeof加length属性
数组有length属性,object没有,而typeof数组与对象都返回object,所以我们可以这么判断

执行:

typeof都返回object

如果你不优先判断Array,比如:

o typeof is object
a typeof is object  

var o = { 'name':'lee' };
var a = ['reg','blue'];
 
var getDataType = function(o){
    if(o instanceof Array){
        return 'Array'
    }else if( o instanceof Object ){
        return 'Object';
    }else{
        return 'param is no object type';
    }
};
 
alert( getDataType(o) );    // Object
alert( getDataType(a) );    // Array
alert( getDataType(1) );    // param is no object type
alert( getDataType(true) ); // param is no object type
alert( getDataType('a') );  // param is no object type

复制代码

在JavaScript中所有数据类型严格意义上都是对象,但实际使用中我们还是有类型之分,如果要判断一个变量是数组还是对象使用typeof搞不定,因为它全都返回object

ECMA-262解释:

 代码如下

 代码如下

var o = { 'name':'lee' };
var a = ['reg','blue'];
 
var getDataType = function(o){
澳门三合彩票,    if(o instanceof Object){
        return 'Object'
    }else if( o instanceof Array ){
        return 'Array';
    }else{
        return 'param is no object type';
    }
};
 
alert( getDataType(o) );    // Object
alert( getDataType(a) );    // Object
alert( getDataType(1) );    // param is no object type
alert( getDataType(true) ); // param is no object type
alert( getDataType('a') );  // param is no object type

new Array([ item0[, item1 [,…]]])
The [[Class]] property of the newly constructed object is set to “Array”.

 代码如下

但数组也是属于object,所以以上两个都是true,因此我们要利用instanceof判断数据类型是对象还是数组时应该优先判断array,最后判断object

var o = { 'name':'lee' };
var a = ['reg','blue'];
 
var getDataType = function(o){
    if(typeof o == 'object'){
        if( typeof o.length == 'number' ){
            return 'Array'; 
        }else{
            return 'Object';    
        }
    }else{
        return 'param is no object type';
    }
};
 
alert( getDataType(o) );    // Object
alert( getDataType(a) );    // Array
alert( getDataType(1) );    // param is no object type
alert( getDataType(true) ); // param is no object type
alert( getDataType('a') );  // param is no object type

复制代码

function isArray(obj) {   
return Object.prototype.toString.call(obj) === '[object Array]';    
}

复制代码

本文由澳门三合彩票发布于服务器&运维,转载请注明出处:据此代码 3 中 pig 是 Pig 的实例,假设要一口咬住

关键词: