原生js 实现继承的常用方法

86 阅读2分钟

在 JavaScript 中,实现继承的常用方法有以下几种:

  1. 原型链继承:

    function Parent() {
      this.name = 'Parent';
    }
    
    function Child() {
      this.age = 10;
    }
    
    Child.prototype = new Parent();
    
    var child = new Child();
    console.log(child.name); // 输出:Parent
    

    优点:

    • 简单易懂,易于实现。
    • 可以继承父类的属性和方法。

    缺点:

    • 子类实例共享父类实例的属性和方法,可能导致子类实例的修改影响其他子类实例。
    • 无法向父类构造函数传递参数。
  2. 构造函数继承(借用构造函数):

    function Parent(name) {
      this.name = name;
    }
    
    function Child(name, age) {
      Parent.call(this, name);
      this.age = age;
    }
    
    var child = new Child('Child', 10);
    console.log(child.name); // 输出:Child
    

    优点:

    • 可以向父类构造函数传递参数。
    • 避免了原型链继承中共享属性和方法的问题。

    缺点:

    • 无法继承父类原型链上的属性和方法。
  3. 组合继承(原型链继承 + 构造函数继承):

    function Parent(name) {
      this.name = name;
    }
    
    Parent.prototype.sayHello = function() {
      console.log('Hello, ' + this.name);
    }
    
    function Child(name, age) {
      Parent.call(this, name);
      this.age = age;
    }
    
    Child.prototype = new Parent();
    Child.prototype.constructor = Child;
    
    var child = new Child('Child', 10);
    console.log(child.name); // 输出:Child
    child.sayHello(); // 输出:Hello, Child
    

    优点:

    • 继承了父类构造函数的属性。
    • 继承了父类原型链上的属性和方法。
    • 可以向父类构造函数传递参数。

    缺点:

    • 调用了两次父类构造函数,一次在原型链继承中,一次在构造函数继承中。
  4. 原型式继承:

    function createObject(obj) {
      function F() {}
      F.prototype = obj;
      return new F();
    }
    
    var parent = {
      name: 'Parent',
      sayHello: function() {
        console.log('Hello, ' + this.name);
      }
    };
    
    var child = createObject(parent);
    child.name = 'Child';
    console.log(child.name); // 输出:Child
    child.sayHello(); // 输出:Hello, Child
    

    优点:

    • 简单易懂,可以实现对象之间的浅拷贝。

    缺点:

    • 无法实现多层继承,只能继承一个对象的属性和方法。
  5. 寄生式继承:

    function createChild(parent) {
      var child = Object.create(parent);
      child.age = 10;
      return child;
    }
    
    var parent = {
      name: 'Parent',
      sayHello: function() {
        console.log('Hello, ' + this.name);
      }
    };
    
    var child = createChild(parent);
    console.log(child.name); // 输出:Parent
    child.sayHello(); // 输出:Hello, Parent
    

    优点:

    • 可以在继承的基础上添加额外的属性和方法。

    缺点:

    • 无法实现多层继承,只能继承一个对象的属性和方法。

需要根据具体的需求和场景选择适合的继承方法。组合继承是常用的继承方式,综合了原型链继承和构造函数继承的优点。如果需要更灵活的继承方式,可以考虑使用 ES6 的类和 extends 关键字来实现继承。