构造函数中的可覆盖方法调用 - 调用该方法的正确方法是什么?

时间:2014-02-13 17:44:58

标签: java

这两个电话有什么区别?该如何正确完成?

//package test;

public class SomeClass {

    public SomeClass() {

        doSomething();//Warning - Overridable method call in constructor
        SomeClass.this.doSomething();//Seems OK
    }

    public void doSomething() {
        //...
    }
}

我想在同一个班级中使用doSomething()。我无意后来改写它。一个想法是声明它final。但是仍然不清楚在这种情况下SomeClass.this.doSomething();是否可以安全使用。

1 个答案:

答案 0 :(得分:2)

编译器警告通知稍微说明会发生什么。如果子类重写doSomething方法,它可以在创建类实例时更改行为,这可能是危险的,也可能不是,具体取决于您的设计。请注意,这是一个警告,而不是编译器异常。

为了证明这一点,只需扩展您的代码进行测试:

class SomeClass {

    public SomeClass() {

        doSomething();//Warning - Overridable method call in constructor
        SomeClass.this.doSomething();//Seems OK, but is not
    }

    public void doSomething() {
        System.out.println("parent");
    }
}

public class SomeOtherClass extends SomeClass {
    @Override
    public void doSomething() {
        System.out.println("child");
    }

    public static void main(String[] args) {
        SomeClass a = new SomeClass();
        SomeOtherClass b = new SomeOtherClass();
    }
}

打印:

parent
parent
child
child

如果您只是希望其他类无法覆盖doSomething方法,请将其标记为final

class SomeClass {

    public SomeClass() {

        doSomething();//Warning - Overridable method call in constructor
        SomeClass.this.doSomething();//Seems OK
    }

    public final void doSomething() {
        System.out.println("parent");
    }
}

然后,如果任何子类试图覆盖它,编译器将抛出错误:

public class SomeOtherClass extends SomeClass {
    @Override
    public void doSomething() { //compiler error
        System.out.println("child");
    }
    //...
}