理解构造函数和原型对象

prototype、__proto__、constructor,今天,我终于搞清楚了它们之间的关系。

prototype是函数才有的属性。
_proto_是每个对象都有的属性。
首先我们来了解几个概念:构造函数、原型对象、实例。

关于构造函数

  构造函数与其他函数的唯一区别,就在于调用它们的方式不同。任何函数,只要通过new操作符来调用,那它就可以作为构造函数;而任何函数,如果不通过new操作符来调用,那它跟普通函数也不会有什么两样。
比如说:
var person = new Object();
这行代码创建了Object引用类型的一个新实例。使用的构造函数是Object。

关于原型对象

  每个函数都有一个prototype(原型)属性,这个属性是一个指针,指向该函数的原型对象。因此,构造函数的prototype(原型)属性指向这个构造函数的原型对象。
  所有原型对象都会自动获得一个constructor(构造函数)属性,这个属性包含一个指向prototype属性所在函数的指针。这句话的意思就是:Person.prototype.constructor == Person

关于实例

  当调用构造函数创建一个新实例后,该实例的内部将包含一个指针,指向构造函数的原型对象。ECMA-262第5版中管这个指针叫[[Prototype]]。虽然在脚本中没有标准的方式访问[[Prototype]],但Firefox、Safari和Chrome在每个对象上都支持一个属性__proto__

三者之间的关系


function Person(){}
Person.prototype.name = “Nicholas”;
Person.prototype.age = 29;
Person.prototype.job = “Software Engineer”;
Person.prototype.sayName = function(){
alert(this.name);
}
var person1 = new Person();

以上面的代码为例,构造函数即指Person,原型对象即Person.prototype,Person的实例即person1。
下图展示各个对象之间的关系:
各个对象之间的关系
总结它们之间的关系如下:

  • Person.prototype指向原型对象;
  • Person.prototype.constructor指向Person;
  • person1.__proto__指向Person.prototype;
  • person1.constructor指向Person;
  • 指向可以理解为(==)。