
本文旨在帮助开发者解决在JavaScript类继承中遇到的“Uncaught TypeError: (intermediate value).updateUI is not a function”错误。通过分析问题原因和提供解决方案,本文将指导读者正确地在子类中调用和扩展父类方法,避免常见的继承陷阱。
在JavaScript中使用class关键字进行面向对象编程时,继承是一种强大的特性,允许子类继承父类的属性和方法。然而,在实际开发中,有时会遇到子类无法访问或调用父类方法的情况,导致TypeError。本文将深入探讨这种问题的常见原因以及相应的解决方案。
问题分析
在提供的代码示例中,RosterTableUtil是父类,RosterSchedulerTableUtil是子类。父类RosterTableUtil的constructor中定义了一个名为updateUI的函数,并将其赋值给this.updateUI。子类RosterSchedulerTableUtil试图通过super.updateUI(cellIndex, rowIndex)调用父类的updateUI方法,但却出现了“Uncaught TypeError: (intermediate value).updateUI is not a function”错误。
立即学习“Java免费学习笔记(深入)”;
问题根源在于父类updateUI的定义方式。在constructor内部使用this.updateUI = (cellIndex, rowIndex) => { ... } 定义的函数,实际上是在创建实例属性,而不是定义类的方法。 虽然在父类实例中可以访问,但是在子类中通过super调用时,由于作用域和this指向的问题,会导致找不到该方法。
解决方案
为了解决这个问题,应该将updateUI定义为类的实例方法,而不是在构造函数中赋值。以下是修改后的代码示例:
class RosterTableUtil {
#highLightCellIndex = -1
#highLightRowIndex = -1;
updateUI (cellIndex, rowIndex) {
this.#highLightCellIndex = cellIndex;
this.#highLightRowIndex = rowIndex;
console.log(`RosterTableUtil row ${this.#highLightRowIndex}, cell ${this.#highLightCellIndex}`);
}
}
class RosterSchedulerTableUtil extends RosterTableUtil {
updateUI (cellIndex, rowIndex) {
super.updateUI(cellIndex, rowIndex);
// do other stuff
}
}
const util = new RosterSchedulerTableUtil();
util.updateUI(1,2);
util.updateUI(3,4);代码解释
- 将updateUI定义为类的方法: 将updateUI函数直接定义在RosterTableUtil类的constructor外部,这样它就成为了类的实例方法。
- 使用super关键字调用父类方法: 在子类RosterSchedulerTableUtil的updateUI方法中,使用super.updateUI(cellIndex, rowIndex)正确地调用父类的updateUI方法。
注意事项
- this的指向: 在JavaScript中,this的指向取决于函数的调用方式。在类的方法中,this指向类的实例。
- super关键字: super关键字用于调用父类的构造函数或方法。在子类的构造函数中,必须先调用super()才能访问this。
- 私有字段: 代码中使用了 #highLightCellIndex 和 #highLightRowIndex 作为私有字段,这是ES2022引入的特性,可以有效防止外部直接访问和修改类的内部状态。
总结
在JavaScript类继承中,正确地定义和调用父类方法至关重要。通过将方法定义为类的实例方法,并使用super关键字进行调用,可以避免TypeError,并实现代码的复用和扩展。理解this的指向以及super关键字的用法,是掌握JavaScript面向对象编程的关键。










