3

我想通过应用经典继承在扩展的javascript“类”中调用超级方法。

function Person(name, age) {
    this._name = name;
    this._age = age;
}
Person.prototype.exposeInfo = function() {
    alert(this._name + ' - ' + this._age);    
}

function Employee(name, age) {
    this.parent.constructor.call(this, name, age);
}
Employee.prototype.exposeInfo = function() {
    alert('Call employee');
    this.parent.exposeInfo();    
}

Employee.prototype = Object.create(Person.prototype);
Employee.prototype.constructor = Employee;
Employee.prototype.parent = Person.prototype;


var p1 = new Person('John Doe', 30);
p1.exposeInfo();

var p2 = new Employee('John Foobar (empl.)', 35);
p2.exposeInfo();

JS小提琴

问题是该方法没有在扩展类中被调用,而只是在父类(Person)中被调用。

4

2 回答 2

4

那是因为覆盖exposeInfo被附加到前prototype一个对象,然后被替换:

Employee.prototype = Object.create(Person.prototype);

您需要颠倒顺序,在创建后附加方法prototype

Employee.prototype = Object.create(Person.prototype);
Employee.prototype.constructor = Employee;
Employee.prototype.parent = Person.prototype;

Employee.prototype.exposeInfo = function() {
    // ...
}

您还需要像使用构造函数一样使用.call()or .apply()with exposeInfo

Employee.prototype.exposeInfo = function() {
    alert('Call employee');
    this.parent.exposeInfo.apply(this, arguments);    
}

否则, 的值this将由最后一个成员运算符确定:

// so, calling:
this.parent.exposeInfo();

// is equivalent to:
alert(this.parent._name + ' - ' + this.parent._age);
于 2013-10-24T14:14:56.750 回答
0
// ...

Employee.prototype = Object.create(Person.prototype);
Employee.prototype.constructor = Employee;
Employee.prototype.parent = Person.prototype;

Employee.prototype.exposeInfo = function() {
  this.parent.exposeInfo.apply(this, arguments);
  // ...
}

这是行不通的。

例子:

// ...

Employee.prototype = Object.create(Person.prototype);
Employee.prototype.constructor = Employee;
Employee.prototype.parent = Person.prototype;

Employee.prototype.exposeInfo = function() {
  this.parent.exposeInfo.apply(this, arguments);
  // ...
}

ParttimeEmployee = Object.create(Employee.prototype);
ParttimeEmployee.prototype.constructor = ParttimeEmployee;
ParttimeEmployee.prototype.parent = Employee.prototype;

ParttimeEmployee.prototype.exposeInfo = function() {
  this.parent.exposeInfo.apply(this, arguments);
  // ...
}

var p1 = new Person('Jack', 30);
p1.exposeInfo(); // ok

var p2 = new Employee('Jane', 25);
p2.exposeInfo(); // ok

var p3 = new ParttimeEmployee('John', 20);
p3.exposeInfo(); // infinite recursion !!!

正确版本:

// Person
function Person(name, age) {
  this._name = name;
  this._age = age;
}
Person.prototype.exposeInfo = function() {
  alert(this._name + ' - ' + this._age);    
}

// Employee
Employee.prototype = Object.create(Person.prototype);
Employee.prototype.constructor = Employee;
Employee.parent = Person.prototype; // <--

Employee.prototype.exposeInfo = function() {
  Employee.parent.exposeInfo.apply(this, arguments); // <--
  // ...
}

// ParttimeEmployee
ParttimeEmployee = Object.create(Employee.prototype);
ParttimeEmployee.prototype.constructor = ParttimeEmployee;
ParttimeEmployee.parent = Employee.prototype; // <--

ParttimeEmployee.prototype.exposeInfo = function() {
  ParttimeEmployee.parent.exposeInfo.apply(this, arguments); // <--
  // ...
}

var p1 = new Person('Jack', 30);
p1.exposeInfo(); // ok

var p2 = new Employee('Jane', 25);
p2.exposeInfo(); // ok

var p3 = new ParttimeEmployee('John', 20);
p3.exposeInfo(); // ok
于 2015-11-15T14:21:09.170 回答