原型链

构造函数、原型、实例的关系:

  1. 每个构造函数都有一个原型对象
  2. 原型对象都包含一个指向构造函数的指针
  3. 实例都包含一个指向原型对象的内部指针
    1. function SuperType(){
    2. this.property = true;
    3. }
    4. SuperType.prototype.getSuperValue = function(){
    5. return this.property;
    6. }
    7. function SubType(){
    8. this.subproperty = false;
    9. }
    10. // 创建SuperType实例,并将该实例赋值给 SubType.prototype
    11. SubType.prototype = new SuperType();
    12. SubType.prototype.getSubValue = function(){
    13. return this.subproperty
    14. }
    15. var instance = new SubType()
    16. alert(instance.getSuperValue()) // true
    image.png image.png

SubType继承了SuperType,SuperType继承了Object(函数的默认原型是Object的实例)
instance指向 SubType 的原型,SubType 的原型指向 SuperType
调用 instance.getSuperValue()搜索路径:

  1. 搜索实例
  2. 搜索SubType.prototype
  3. 搜索SuperType.prototype

    instanceof、isPrototypeOf

instanceof:检测构造函数的 prototype 属性是否出现在某个实例对象的原型链上

  1. alert(instance instanceof Object)
  2. alert(instance instanceof SuperType)
  3. alert(instance instanceof SubType)

isPrototypeOf:检查一个对象是否存在于另一个对象的原型链上

  1. alert(Object.prototype.isPrototypeOf(instance))
  2. alert(SuperType.prototype.isPrototypeOf(instance))
  3. alert(SubType.prototype.isPrototypeOf(instance))

原型链的问题

引用类型值的原型属性会被所有实例共享

  1. function SuperType(){
  2. this.colors = ["red","blue","green"]; // 数组(引用类型值)
  3. }
  4. function SubType(){}
  5. SubType.prototype = new SuperType(); // 继承 SuperType
  6. var instance1 = new SubType();
  7. instance1.colors.push("black");
  8. alert(instance1.colors); // "red,blue,green,black"
  9. var instance2 = new SubType();
  10. alert(instance2.colors); // "red,blue,green,black"

构造函数

使用 apply()call()方法在新创建的对象上执行构造函数
在子类型构造函数中向超类型构造函数传递参数

  1. function SuperType(name){
  2. this.colors = ["red","blue","green"];
  3. this.name = name;
  4. }
  5. function SubType(){
  6. SuperType.call(this,"fanison"); // 继承 SuperType,同时传递参数(为SubType实例设置name属性)
  7. this.age = 18; // 实例属性
  8. }
  9. var instance1 = new SubType();
  10. instance1.colors.push("black");
  11. console.log(instance1.colors,instance1.name,instance1.age) // "red,blue,green,black" "fanison" 18
  12. var instance2 = new SubType();
  13. console.log(instance2.colors,instance2.name,instance2.age) // "red,blue,green,black" "fanison" 18

image.png

组合继承

使用原型链实现对原型属性和方法的继承,通过构造函数实现对实例属性的继承

  1. function SuperType(name){
  2. this.colors = ["red","blue","green"];
  3. this.name = name;
  4. }
  5. SuperType.prototype.sayName = function(){
  6. alert(this.name);
  7. }
  8. function SubType(name,age){
  9. SuperType.call(this,name); // 继承属性
  10. this.age = age;
  11. }
  12. // 继承方法
  13. SubType.prototype = new SuperType();
  14. SubType.prototype.constructor = SubType;
  15. SubType.prototype.sayAge = function(){
  16. alert(this.age);
  17. };
  18. var instance1 = new SubType("fanison",18);
  19. instance1.colors.push("black");
  20. console.log(instance1.colors); // "red,blue,green,black"
  21. instance1.sayName(); // "fanison"
  22. instance1.sayAge(); // 18
  23. var instance2 = new SubType("yafanison",20);
  24. console.log(instance2.colors); // "red,blue,green,black"
  25. instance2.sayName(); // "yafanison"
  26. instance2.sayAge(); // 20

image.pngimage.png