原型鏈模式-拓展

批量設置原型上的原型和方法
方法一

    var pro = Fn.prototype; // 把原來原型指向的地址賦值給pro,現在他們操作的是同一個內存地址
    pro.getX = function () {
        console.log(this.x);
    }
    pro.getY = function () {

    }
    var f1 = new Fn();

方法二
重構原型對象的方式 -> 自己新開辟一個堆內存,存儲公有屬性和方法,把瀏覽器原來給Fn.prototype開辟的那個替換掉。

    function Fn() {
        this.x = 100;
    }
    Fn.prototype = {
        // 手動增加constructor指向:
        constructor: Fn,
        a: function () {

        },
        b: function () {

        },
        c: function () {

        }
    }
    var f = new Fn();
    f.a();
    f.b();
    f.c();
  1. 只有瀏覽器天生給Fn.prototype開辟的堆內存里面才有constructor,而我們自己開辟的這個堆內存沒有這個屬性, 這樣constructor指向就不再是Fn而是Object了。
    console.log(f.constructor); // -> 沒做任何處理前,Object
    // 為了和原來的保持一致,需要手動的增加constructor指向
  1. 用這種方式給內置類增加公有的屬性
    例如:給內置類Array增加一個數組去重的方法
    Array.prototype.unique = function () {

    }
    Array.prototype = {
        constructor: Array,
        unqiue: function () {
            // 這種方式不行
        }
    }
    console.dir(Array.prototype);

這種方式會把之前存在于原型上的屬性和方法替換掉,所以用這種方式修改內置類的話,瀏覽器是會將其屏蔽的。
但是我們可以一個個的修改內置類的方法,通過下述方式在數組的原型上增加方法,如果方法名和原來內置的重復了,會把內置的方法修改了。 -> 我們以后再內置類的原型上增加方法,命名都需要加特殊的前綴。

    Array.prototype.sort = function () {
        console.log(this); // this -> ary 當前要操作的數組
    }
    var ary = [1, 2, 3, 3, 1, 3, 4, 12];
    ary.sort();

在原型模式中,this常用的有兩種情況:
在類中,this.xxx = xxx;this -> 當前類的實例。
某一個方法中的this -> 看執行的時候 "." 前面是誰,this就是誰。

  1. 需要先確定this的指向(即this是誰)。
  2. 把this替換成對應的代碼。
  3. 按照原型鏈查找的機制,一步步的查找結果。
    function Fn() {
        this.x = 100;
        this.y = 200;
        this.getY = function () {
            console.log(this.y);
        }
    }
    Fn.prototype = {
        constructor: Fn,
        y: 300,
        getX: function () {
            console.log(this.x);
        },
        getY: function () {
            console.log(this.y);
        }
    };
    var f = new Fn();
    f.getX(); // -> console.log(f.x) -> 100
    f.__proto__.getX(); // -> this 是f.__protoo_ -> console.log(f.__proto__.x) -> undefined
    Fn.prototype.getX(); // -> this 是Fn.prototype -> Fn.prototype.x -> undefined

    f.getY(); // -> f.y -> 200
    f.__proto__.getY(); // -> this是f.__proto__ -> f.__proto__.y -> 300

在內置類的原型上拓展一個方法,用于數組去重

    Array.prototype.myUnique = function () {
        // this -> ary
        var obj = {};
        for (var i = 0; i < this.length; i++) {
            var cur = this[i];
            if (obj[cur] === cur) {
                this[i] = this[this.length - 1];
                this.length--;
                i--;
                continue;
            }
            obj[cur] = cur;
        }
        obj = null;
        return this; // 目的是為了實現鏈式寫法
    }

鏈式寫法:執行完數組的一個方法,可以緊接著執行下一個方法。
原理:
ary為什么可以使用sort方法? -> 因為sort是Array.prototype上的公有的方法,而數組是ary是Array的一個實例,所以ary可以使用sort方法 -> 只有數組才能使用Array原型上定義的屬性和方法。
sort執行完成的返回值是一個排序后的"數組",所以可以繼續執行reverse()。
reverse執行完成的返回值也是一個"數組",所以可以繼續執行pop()。
pop()執行完成的返回值是被刪除的最后一個元素,不是一個數組了,所以在執行數組相關操作會報錯。

    ary.sort(function (a, b) {
        return a - b;
    }).reverse().pop();
    ary.myUnique(); // this -> ary
    Array.prototype.myUnique(); // this -> Array.prototype
    console.log(ary);
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容