类与接口的方法重写:子类重写同名方法时覆盖哪一方?
当子类继承父类并实现同签名方法的接口时,重写的方法到底对应哪一方?
这个问题其实挺接地气的,很多人第一次碰到这种场景都会懵——我来给你拆解明白:子类的重写方法会同时覆盖父类的实例方法,并且完成接口抽象方法的实现,具体可以分两种情况来看:
情况1:父类的方法是可继承的(非private)
举个Java代码的例子最直观:
首先定义父类A:
class A { public void doSomething() { System.out.println("父类A的doSomething"); } }
再定义接口I:
interface I { // 接口方法默认是public abstract,不用显式声明 void doSomething(); }
然后是子类B,继承A并实现I,同时重写doSomething:
class B extends A implements I { @Override // 这个注解编译器完全认可,因为它既适配父类重写,也适配接口实现 public void doSomething() { System.out.println("子类B的doSomething"); } }
我们写个测试类验证:
public class TestDemo { public static void main(String[] args) { // 用父类A的引用指向子类对象 A aInstance = new B(); aInstance.doSomething(); // 输出:子类B的doSomething —— 说明覆盖了父类的方法 // 用接口I的引用指向子类对象 I iInstance = new B(); iInstance.doSomething(); // 输出:子类B的doSomething —— 说明实现了接口的方法 } }
为什么会这样?因为Java里接口的方法是抽象的,必须由实现类提供具体逻辑;而父类的实例方法是可继承的,子类重写后就会替换掉父类的实现。此时子类的这一个方法,同时满足了两个要求:既完成了接口的实现义务,又覆盖了父类的方法逻辑。
情况2:父类的方法是private的
如果父类的方法是private的,那情况就不一样了——因为private方法不会被子类继承,所以子类的方法只是单纯实现接口的抽象方法,和父类的private方法完全无关。
比如修改父类A:
class A { private void doSomething() { System.out.println("父类A的private doSomething"); } }
子类B的代码不变,此时@Override注解不会报错——因为这里的doSomething是实现接口的方法,而父类的private方法对子类不可见,所以子类的方法是全新的实现,和父类的方法没有重写关系。
总结一下
- 当父类的方法是可继承的(非private、非static),子类的重写方法同时覆盖父类方法 + 实现接口方法;
- 当父类的方法是private,子类的方法只是实现接口方法,和父类的方法无关联。
内容的提问来源于stack exchange,提问作者Fego
相关产品推荐
相关产品推荐

