美文网首页
JS的原型链相关(待续)

JS的原型链相关(待续)

作者: 郝翔 | 来源:发表于2016-07-13 09:11 被阅读18次

    首先列出经常会听到的属性,之后来说明它们之间的关系,再进一步解释如何通过这些属性构建JS的层层继承。

    属性

    proto所有的对象都拥有这个属性,这个属性是继承的关键。
    prototype是函数独有的一个属性,在使用new来构建新对象时,它与新对象的proto属性有关。
    __proto属性与prototype属性都是对象。

    这些属性本身没有什么特别,但它们之间的关系却比较复杂,下面加上代码的印证,说清楚他们之间的关系。

    基础实现

    这里新建一个函数,函数也是对象,它有自己的属性,我们为它的prototype(原型链)属性添加一个方法introduce,之后通过new方法新建一个子类,输出子类car的name属性,调用子类的方法

    function Car (name) {
        this.name = name;
    }
    Car.prototype.introduce = function () {
        console.log('Hello, my name is: ' + this.name);
    }
    var car = new Car('Alice');
    console.log(car.name);
    car.introduce();
    

    继承的实现

    我们学习面向对象的编程语言,很多时候是为了提高效率和正确性,而继承是实现这两点的关键,既然需要实现继承,那么来JS中是如何实现的。

    JS创造了prototype属性在通过函数构造子类时生成proto属性,通过proto_属性来连接子类和父类。

    于是,我们先从prototype属性说起,先明确一点,这个属性是函数特有的,这个属性的作用是为了在使用new来构造新对象实例时,可以让对象实例共享一些函数。

    对于上面的代码,在使用Car这个构造函数构建的对象实例后,所有的新构建的对象实例都会拥有方法introduce。
    理解了这里,我们来整体看一次。
    先定义一个构造函数Car,之后为其原型添加方法,接着使用new标识符通过构造函数来新建一个对象。等等,这里需要听一下,为什么一个new可以有这么大的作用,这里面发生了什么?

    new

    那我们先说说new,它的确执行了好几个步骤,才产生了一个新对象。

    1. 首先新建一个空对象car,每个对象在创建之后,就会拥有一个proto隐藏属性,这个属性会原本指向Object属性的原型对象,可以通过下面的代码一窥究竟
    var a = {}
    a.__proto__
    Object {}
        __defineGetter__:__defineGetter__()
        constructor:Object()
        ...
    a.__proto__ === Object.prototype
    // true
    
    1. 改变proto属性的指向,将它指向Car函数的prototype属性
    2. 让Car函数内部的this指向新建的对象car
    3. 执行构造函数,构造函数也是函数,但这个构造函数并没有返回任何值,但在它执行的过程中,由于this是指向新对象car的,所以它会为car的name属性赋值。执行完毕后,car对象会拥有name属性。

    原型链上的方法

    由于现在car.proto引用了Car.prototype引用的对象,那么他们会共享属性。

    相关文章

      网友评论

          本文标题:JS的原型链相关(待续)

          本文链接:https://www.haomeiwen.com/subject/stntjttx.html