接口方法必须为public且非static、non-final;实现类重写时必须显式声明public,否则编译报错;多接口同名方法需签名一致,返回类型支持协变,异常需兼容;抽象类可不实现接口所有方法;建议强制使用@Override注解。

接口方法必须被 public 且非 static、non-final
Java 接口中定义的方法默认是 public abstract,哪怕你不写修饰符。实现类里重写这些方法时,public 修饰符不能省略——否则编译报错:error: method does not override or implement a method from a supertype。这是因为子类方法的访问权限不能比父接口更严格。
- 接口方法不能是
private、protected或包私有(默认) -
static和default方法在接口中允许存在,但它们不参与“被实现”的逻辑;只有abstract方法才需要在实现类中提供具体体 - 实现类中不能用
final修饰重写的方法(除非该方法本身在接口中是default且你只是调用它)
一个类实现多个接口时,方法签名冲突怎么办
如果两个接口都声明了同名同参数的方法(比如都定义了 void start()),实现类只需提供一个实现即可,不会报错。但如果返回类型不同(如一个接口要求 String start(),另一个要求 int start()),编译器直接拒绝——因为 Java 不允许仅靠返回类型区分重载,更不允许这种协变冲突。
- 若两个接口的同名方法参数一致但返回类型是父子关系(如
Object getValue()vsString getValue()),Java 允许协变返回,实现类可用子类型返回(String) - 若方法抛出的异常不兼容(一个声明
throws IOException,另一个throws SQLException),实现类方法不能同时满足两者,需统一处理或包装成运行时异常 - 常见陷阱:误以为
default方法可以“自动合并”,其实冲突时仍需手动覆盖
抽象类实现接口时可以不实现所有方法
抽象类可以声明实现某个接口,但不必提供接口中所有 abstract 方法的具体实现——只要它自己也声明为 abstract。这点和普通类不同,普通类(非 abstract)必须实现接口全部抽象方法。
public abstract class BaseProcessor implements Runnable {
// 没有实现 run() 方法,合法
public void init() { /* ... */ }
}- 子类继承该抽象类时,要么继续抽象(不实现
run()),要么最终给出public void run()实现 - 注意:即使抽象类提供了
default方法的实现,子类仍可选择重写,不强制继承 - 别混淆
implements和extends:抽象类只能extends一个类,但可implements多个接口
接口方法实现中容易忽略的 @Override 注解
虽然 @Override 对编译不是必需的,但强烈建议加上。它能帮你提前发现拼写错误、参数类型写错、泛型擦除导致的签名不匹配等问题。例如把 void process(List 错写成 void process(ArrayList,没加 @Override 可能变成新增方法而非重写,逻辑静默失效。
立即学习“Java免费学习笔记(深入)”;
- IDE(如 IntelliJ)默认对实现接口方法自动插入
@Override - 若接口后续升级增加新方法,未加
@Override的实现类不会报错,但可能漏掉新契约 - Java 9+ 中,
@Override也可用于实现default方法,同样起校验作用
接口方法实现看着简单,真正踩坑多在权限修饰符、多继承冲突、抽象层级混用和注解缺失这几个点上。尤其当项目用到大量函数式接口或 Spring 的回调接口时,一个没写 public 或漏了 @Override,问题往往延迟到运行时才暴露。










