javascript面向对象编程学习(二) —— 原型链继承

570 阅读1分钟

导读

javascript面向对象编程学习(一)

1. 构造函数、原型和实例的之间的关系:

每个构造函数都有一个原型对象prototype,原型对象包含一个指向构造函数的指针constructor,而实例都包含一个指向原型对象的内部指针__proto__。我们可以利用它们的关系,实现原型链继承!

1.1 假设有两个构造函数 Person和Child,它们自身关系如下:

原型链继承之前

2. 实现原型链继承

function Person(name) {
  this.name = name;
  this.names = ['大魔王']
}

Person.prototype.say = function() {
  console.log('my name is ' + this.name);
}

function Child() {}

const person = new Person('大魔王');

// Child的原型对象被更改为person实例
Child.prototype = person;

Child.prototype.getName = function() {
  console.log(this.name);
}

Child.prototype.getNames = function() {
    console.log(this.names)
}

var child = new Child();

child.say(); // my name is 大魔王
child.getName(); // 大魔王

2.1 它们新的关系如下:

原型链继承

在上图可以看到,
构造函数Child的原型对象prototype被修改为person实例,
child实例通过__proto__指向Child的原型对象,即person实例。

 console.log(Child.prototype === person) // true
 console.log(child.__proto__ === person) // true 

3. 原型链继承的缺点

使用原型创建对象会存在多个实例对引用类型的操作会被篡改的问题,如下:

child.names.push('我不是大魔王');
child.getNames(); // ["大魔王", "我不是大魔王"]
var child2 = new Child();
child2.getNames(); // ["大魔王", "我不是大魔王"]

childchild2两个实例的names属性指向相同,操作其中一个,另一个也会被影响。

3.1 缺点有三 :

  1. 原型链继承多个实例的引用类型属性指向相同,一个实例修改了原型属性,另一个实例的原型属性也会被修改。
  2. 不能传递参数。
  3. 继承单一。

4. tip

有错误请指出,大家互相学习