在抽象类的构造函数中使用抽象init()函数
我有这样的事情:
public abstract class Menu { public Menu() {
init();
}
protected abstract void init();
protected void addMenuItem(MenuItem menuItem) {
// some code...
}
}
public class ConcreteMenu extends Menu {
protected void init() {
addMenuItem(new MenuItem("ITEM1"));
addMenuItem(new MenuItem("ITEM2"));
// ....
}
}
//Somewhere in code
Menu menu1 = new ConcreteMenu();
如您所见,超类的init方法是抽象的,并在创建对象后由构造函数自动调用。
当我需要创建这种类型的对象且其结构不会及时更改时,我很好奇我是否会遇到这样的代码问题。
有什么更好的办法吗?它可以在Java中运行,但是可以在C ++和ActionScript中运行吗?
谢谢你的答案。
回答:
请勿从构造函数中调用过多的方法。
引用 有效Java 2nd Edition,条款17:继承的设计和文档,或者禁止它 :
类必须遵守一些其他限制以允许继承。 直接或间接
。如果违反此规则,将导致程序失败。超类构造函数在子类构造函数之前运行,因此子类中的重写方法将在子类构造函数运行之前被调用。如果重写方法依赖于子类构造函数执行的任何初始化,则该方法将无法正常工作。
这是一个示例说明:
public class ConstructorCallsOverride { public static void main(String[] args) {
abstract class Base {
Base() { overrideMe(); }
abstract void overrideMe();
}
class Child extends Base {
final int x;
Child(int x) { this.x = x; }
@Override void overrideMe() {
System.out.println(x);
}
}
new Child(42); // prints "0"
}
}
在此,当Base
构造函数调用时overrideMe
,Child
尚未完成对的初始化final int
x,并且该方法获得了错误的值。这几乎肯定会导致错误和错误。
也可以看看
- FindBugs-从超类的构造函数调用的未初始化的字段方法读取
以上是 在抽象类的构造函数中使用抽象init()函数 的全部内容, 来源链接: utcz.com/qa/405953.html