原型

要掌握这三者之间的关系prototype,constructor,__proto__
通过代码例子记录一下

function F() {
    this.a = 123;     //             this : {
                      //自身属性             a :123,   
                      //this的.__proto__      Object.creat(F.prototype),    
                      //                    }
};
var o = new F();      //这里o就是this

通过代码看一下

  • prototype做了什么
    默认情况下,将F.prototype的所有属性包括继承的赋值给o.__proto__
    prototype有什么东西呢?

    • 自己的原型链,F.prototype.__proto__
    • prototype添加一个constructor属性,用来指明对象的谁构造的
    • F.prototype自身全部属性,(这边构建一个空对象原型,所以没有自有属性)
  • constructor,默认指向prototype对象所在的构造函数,必须从对象的原型链上去找也就是F.prototype上去找
  • 对于__proto__,o对象得到了__proto__,这样也就形成了对象之间的链接,构成了原型链,能通过原型链访问继承的属性和方法;当然o还有自身属性a

注意点:当我们自定义了F的原型

function F() {};
F.prototype = {a : 1};
//因为原型指向的改变,需要加上构造器的正确值
F.prototype.constructor = F;
var o = new F();
console.log(o.constructor);
  • 手动改变原型指向,会导致constructor的变更,我们需要手动添加
  • 这种手动添加的constructor是可遍历的,一般这么修改F.prototype.a = 1;
  • 默认constructor在F.prototype中找
  • F.prototype = {a : 1};赋值是引用地址的赋值

    function F() {};
    function G() {};
    var o = new F();
    F.prototype.a = 2;            //修改的还是new时创建的指针指向上的内容
    //F.prototype = {a : 2};      //F.prototype得到新指针,所以new时的指针上的内容不受影响
    console.log(o);
    

继承

继承要实现的效果是:

  • 子类和父类存在继承关系
function F() {
    this.f = "f"
}
function Son() {
    this.s = "s"
}
var po = {a : 1};
F.prototype = po;
//第一种,是错误的
//Son.prototype = F.prototype;   //两者是同辈分,之间不存在继承,是兄弟

//第二种
Son.prototype = Object.create(F.prototype);   //Son.prototype.__proto__ = F.prototype 这个就是存在上下辈分,有继承关系

//第三种
//Son.prototype = new F();     与第二种一样,有继承关系,但是这种会进行一次F构造函数的构建,消耗性能   

所以我们采用Son.prototype = Object.create(F.prototype);

  • 拥护父类自身的属性及方法

利用call加this机制完成子类对父类自身方法属性的继续

function F() {
    this.f1 = '1',
    this.fn = function () {
        console.log(this)
    }
}
function Son() {
    F.call(this);
}
var son = new Son();
console.log(son.fn())
  • 构造器的修改Son.prototype.constructor = Son;使得son知道由Son构建自己

整合一下

function F() {
    this.f1 = '1';
    
}

function Son() {
    F.call(this);
    
}

F.prototype.fn = function () {};

var inherit = (function (){
    return function inherit(Target, Origin){
            Target.prototype = Object.create(Origin.prototype);
            //create等价于
            // function F() {};
            // F.prototype = Origin.prototype;
            // new F()
            Target.prototype.constructor = Target;

        }
}());
inherit(Son, F);
var son = new Son();
console.log(Object.getPrototypeOf(son));

Infinity
293 声望9 粉丝

学前端中,只想激情优雅的写代码