關於JS的clone()函數編寫的一些問題

問題講述:用js 實現一個clone()克隆函數,該函數會把輸入進去的不一樣類型值Number,String,Undefined,Boolean,Function,Null,Object,Array,RegExp,克隆一份出來正則表達式

1、解題代碼

直接貼代碼,數組

function clone(obj){
            var copy;
            switch(typeof obj){
                case 'undefined':break;
                case 'number':
                case 'string':
                case 'boolean':
                case 'function':copy = obj;break;
                case 'object':
                    if(obj == null) copy = null;
                    else if(toString.call(obj) === '[object Array]')
                    {
                        copy = [];
                        for(var i in obj) copy.push(clone(obj[i]));
                    }
                    else if(toString.call(obj) === '[object RegExp]')
                    {
                        copy = obj;
                    }
                    else 
                    {
                        copy = {};
                        for(var j in obj)
                            copy[j]= clone(obj[j]);
                    }
            }
            return copy;
        }
        var a=undefined;
        var b=1;
        var c="Hello";
        var d=true;
        var add=function(a,b){
            return a+b;
        }
        var e=null;
        var f=[1,2,3];
        var g=/^\s+/;
        var h={
            a:1,
            b:2
        }
        console.log(typeof clone(a));
        console.log(typeof clone(b));
        console.log(typeof clone(c));
        console.log(typeof clone(d));
        console.log(clone(add)(1,2));
        console.log(Object.prototype.toString.call(clone(e)));
        console.log(Object.prototype.toString.call(clone(f)));
        console.log(Object.prototype.toString.call(clone(g)));
        console.log(Object.prototype.toString.call(clone(h))); 

結果:函數

2、疑問

一開始看到這個問題的時候,就想到typeof [1,2,3]的結果是,這可怎麼辦,正則表達式,null,object的typeof都是。看上面的代碼,是用Object.prototype.toString.call(obj)或者toString.call(obj)來解決的。spa

那爲何不直接用obj.toString()呢?咱們先來看看obj.toString()會輸出什麼?prototype

null和undefined竟然出錯了,這是確定的,由於toString()不可完成null和undefined的轉型,用String()才能夠code

若String()轉換的不是null或者undefined,則自動轉換爲toString().扯遠了。。咱們說回正題對象

那麼用Object.prototype.toString.call(obj)的結果是什麼呢?blog

竟然不同,這是怎麼回事?原型

原來,雖然Array,Null等類型雖然是Object的實例,可是他們各自都重寫了toString()方法,咱們試着來驗證一下:string

var arr=[1,2,3];
console.log(Array.prototype.hasOwnProperty("toString"));//判斷原型中是否有toString()方法
console.log(arr.toString());
delete Array.prototype.toString;//刪除Array原型裏面重寫的toString
console.log(Array.prototype.hasOwnProperty("toString"));
console.log(arr.toString());

結果:

很明顯真的被改寫了。

3、還有一些話

其實有人會說能夠用arr instanceof Array來判斷是否爲數組,其實instanceof在跨frame對象構建的場景下會失效。

相關文章
相關標籤/搜索