NullPointerException,因为覆盖了函数和超类的调用



以下设置:

public class Superclass
{
    private String params;
    public Superclass(String params)
    {
        this.params = params;
        doStuff();
    }
    public void doStuff()
    {
        // uninteresting stuff
    }
}
public class Subclass extends Superclass
{
    private Object someObject;
    public Subclass(String params, Object someObject)
    {
        super(params);
        this.someObject = someObject;
    }
    @Override
    public void doStuff()
    {
        someObject.toString(); // <- causes NullPointerException
    }
}

超类创建一个用户界面,而子类应该创建一个更专业的版本。

从软件工程的角度来看,当"子类"仍然扩展"超类"时,防止NullPointerException的最干净方法是什么?

父类在构造时没有明显的理由调用doStuff

简单地说,不要把电话放在那里。 这些类应彼此独立地构造。 父类不应依赖于来自子类的任何数据来完成其构造;在父构造函数中调用的子项重写的任何方法都将引入此依赖项。

但是,如果您确实发现需要在父级中调用额外的方法,则可以创建一个final方法,并且不会发生不良影响,因为子方法无法访问该方法。

public class Superclass {
    private String params;
    public Superclass(String params) {
        this.params = params;
        doStuffParent();
    }
    public final void doStuffParent() {
        // uninteresting stuff
    }
    public void doStuff() {
        // uninteresting stuff...again?
    }
}

从软件工程的角度来看,您正在尝试对尚未构造的对象执行操作。将这个想法映射到你的真实类及其工作,你会明白超类构造函数存在一些问题,因为它试图在一个糟糕的状态下工作。

话虽如此,您有几个选择。

  • 如果有意义,请尝试将Object someObject传递给超类。 可能是超级类真的需要它才能工作。
  • 不要在超类构造函数中调用doStuff()。在两个构造函数之外显式调用它甚至可能是有意义的。
  • 让扩展类的构造函数调用 doStuff(..)

最新更新