如何在javascript中从子类调用父方法?

2022-08-30 01:02:06

在过去的几个小时里,我一直试图找到解决问题的方法,但似乎毫无希望。

基本上,我需要知道如何从子类调用父方法。到目前为止,我尝试过的所有东西最终都无法正常工作或覆盖父方法。

我正在使用以下代码在javascript中设置OOP:

// SET UP OOP
// surrogate constructor (empty function)
function surrogateCtor() {}

function extend(base, sub) {
    // copy the prototype from the base to setup inheritance
    surrogateCtor.prototype = base.prototype;
    sub.prototype = new surrogateCtor();
    sub.prototype.constructor = sub;
}

// parent class
function ParentObject(name) {
    this.name = name;
}
// parent's methods
ParentObject.prototype = {
    myMethod: function(arg) {
        this.name = arg;
    }
}

// child
function ChildObject(name) {
    // call the parent's constructor
    ParentObject.call(this, name);
    this.myMethod = function(arg) {
        // HOW DO I CALL THE PARENT METHOD HERE?
        // do stuff
    }
}

// setup the prototype chain
extend(ParentObject, ChildObject);

我需要先调用父级的方法,然后在子类中向其添加更多内容。

在大多数OOP语言中,这就像调用一样简单,但我真的无法理解它在javascript中是如何完成的。parent.myMethod()

任何帮助都非常感谢,谢谢!


答案 1

ES6 样式允许您使用新功能,例如关键字。 关键字,当您使用ES6类语法时,它完全与父类上下文有关。举一个非常简单的例子,结账:supersuper

记得:我们不能通过实例方法中的超级关键字调用父静态方法。调用方法也应该是静态的。

通过实例方法调用静态方法 - TypeError !

class Foo {
  static classMethod() {
    return 'hello';
  }
}

class Bar extends Foo {
  classMethod() {
    return super.classMethod() + ', too';
  }
}
console.log(Bar.classMethod()); // 'hello' - Invokes inherited static method
console.log((new Bar()).classMethod()); // 'Uncaught TypeError' - Invokes on instance method

通过超级调用静态方法 - 这有效!

class Foo {
  static classMethod() {
    return 'hello';
  }
}

class Bar extends Foo {
  static classMethod() {
    return super.classMethod() + ', too';
  }
}

console.log(Bar.classMethod()); // 'hello, too'

现在超级上下文根据调用而变化 - 瞧!

class Foo {
  static classMethod() {
    return 'hello i am static only';
  }

  classMethod() {
    return 'hello there i am an instance ';
  }
}

class Bar extends Foo {
  classMethod() {
    return super.classMethod() + ', too';
  }
}

console.log((new Bar()).classMethod()); // "hello there i am an instance , too"
console.log(Bar.classMethod()); // "hello i am static only"

此外,您可以使用 super 来调用父构造函数:

class Foo {}

class Bar extends Foo {
    constructor(num) {
        let tmp = num * 2; // OK
        this.num = num; // ReferenceError
        super();
        this.num = num; // OK
    }
}

当然,您可以使用它来访问 父类属性 。因此,使用ES6并感到高兴。super.prop


答案 2

这是如何完成的:ParentClass.prototype.myMethod();

或者,如果要在当前实例的上下文中调用它,则可以执行以下操作:ParentClass.prototype.myMethod.call(this)

从带有参数的子类调用父方法也是如此:* 提示:使用 apply() 而不是 call() 将参数作为数组传递。ParentClass.prototype.myMethod.call(this, arg1, arg2, ..)