原型

  • prototype、[[prototype]]、constructor 三者之间的关系

Javascript 是弱类型语言,它没有类(Class)的概念,但它通过更灵活的原型(Prototype)实现了类的功能。

TIP

ES6 的 Class 只是语法糖,本质上还是 Prototype。

函数和原型

每个函数都有一个 prototype 对象,该对象有一个指向函数本身的 constructor 属性:

function SuperType(){}
SuperType.prototype = {}

prototype 对象中可以添加自定义属性:

function SuperType(){
    this.value = 'Hello world'
}
SuperType.prototype.getSuperValue = function(){
    return this.value
}

实例和原型

函数的实例对象之所以能访问原型对象是因为实例对象有一个 [[prototype]] 指针指向了原型对象:

var instance = new SuperType()
instance.getSuperValue() // Hello world

浏览器则是通过 __proto__ 属性实现了这个指针:

instance.__proto__=== SuperType.prototype  // true

Function 和 Object

函数都是 Function 创建出来的,所以所有函数的 [[prototype]] 指针都指向 Function.prototype ,而 Function 本身就是一个函数,所以 Function.__proto__ 指向 Function.prototype ,即指向它自己。

对象都是 Object 创建出来的,所以所有的原型对象的 [[prototype]] 指针都指向 Object.prototype,而 Object 又是一个函数,所以 Object.__proto__ 指向 Function.prototype

但作为对象最顶端的 Object.prototype.__proto__ 指向 null

Function.__proto__ === Function.prototype // true
Object.__proto__ === Function.prototype // true

原型链

结合上面的结论可得如下关系图:

这种实例和构造函数以及原型对象之间的关系便是原型链。

总结

  • 函数都是 Function 创建出来的,即所有函数都是 Function 的实例
  • 对象都是 Object 创建出来的,即所有对象都是 Object 的实例
  • prototype 链接的是构造函数和原型对象,__proto__ 链接的是实例对象和原型对象。

参考文章:

Last Updated: 7/16/2020, 11:24:55 PM