个人谈谈对原型和原型链的理解

639 阅读3分钟

##写在前面

  • 从js设计谈起
  • 为什么要设计原型对象
  • 什么是原型对象
  • 对象和函数在原型链中的关系
  • 原型链
  • 小结

##从js设计谈起

JS中的数据类型设计受当时Java流行的影响,都是对象类型,但是有对象必然要涉及到继承的实现,这时JS该怎么去实现这个继承机制,如果设计的和java一样,就要引入类的概念,就变成和java一样是一种完全面向对象的语言了。但是JS还是决定自己设计一种继承机制。但是他的设计思想还是采用了java的一些特性。

通常 Java 生成对象是通过 new 的方式,通过类生成一个实例对象的过程。但是 JS 中并没有类,那 JS 的设计者要怎么做?

他找到了 Java 和 JS 的共同点就是两者都有构造函数, Java的 new 的过程内部其实调用了构造函数。但是 JS 是没有“类”的概念的,于是 JS 就把new 一个“类”设计成了 new 一个构造函数,于是构造函数就可以创建实例对象了。 ##为什么要设计原型对象

上述这样的原型设计有一个致命的缺点就是无法共享公共属性。 因为我们知道,每 new 一个对象,生成的实例是两个不同的对象。所以共有的属性也不是共享的,如果我们改动一个对象的 type 属性,但是另一个不会改变,因为这个属性没有共享。 所以要设计一个对象专门用来存储对象共享的属性,我们就叫它 原型对象 ##什么是原型对象

就是函数上的prototype属性所指向的一个对象就是原型对象 每一个函数都有原型对象 我们也叫他显示原型,我们把所有实例对象共享的属性和方法都放在这个对象中,不需要共享的放在构造函数中。 所以说,实例对象一旦通过构造函数创建,就会自动给实例对象赋值上原型对象上共享的属性或方法。说清楚一点就是该对象属性都指向了原型对象的属性值 ##对象和函数在原型链中的关系

原型链图
总结为一句话为:

构造函数的 prototype 指向原型对象,原型对象有一个 constructor 属性指回构造函数,每个构造函数生成的实例对象都有一个 proto 属性,这个属性指向原型对象。

##原型链 指的就是对象的隐式原型链

##总结

1、所有的实例的_proto_都指向该构造函数的原型对象(prototype)。 2、所有的函数(包括构造函数)是Function的实例,所以所有函数的_proto_的都指向Function的原型对象。 3、所有的原型对象(包括 Function的原型对象)都是Object的实例,所以_proto_都指向 Object(构造函数)的原型对象。而Object构造函数的 _proto_指向 null。 4、Function构造函数本身就是Function的实例,所以_proto_指向Function的原型对象。