Java接口默认方法通过default关键字实现“加行为不破契约”,必须用default修饰、含方法体、仅限接口中声明、默认public;多接口同名default需实现类显式重写并可调用A.super.method()。

Java 接口默认方法通过 default 关键字扩展,核心是“加行为不破契约”——在已有接口中新增带实现的方法,所有老实现类无需修改即可编译通过、运行可用。
怎么写一个有效的 default 方法
语法上必须用 default 修饰,方法体不能为空,且不能是 static、final、synchronized 或 native:
- 声明位置:只能出现在接口中,不能出现在类或抽象类里
- 访问权限:默认是
public,不可写private(Java 9+ 才支持私有 default 方法) - 典型写法:
default void log(String msg) { System.out.println("[LOG] " + msg); } - 返回类型和参数需明确,不支持仅靠返回值类型重载
扩展时必须依赖已有契约
default 方法的逻辑要能稳定跑通,就得基于接口已有的抽象方法或静态工具方法,不能凭空调用实现类才有的东西:
- ✅ 安全做法:复用接口中已定义的
iterator()、size()等抽象方法 - ✅ 推荐做法:把复杂逻辑抽成
public static工具方法,default 方法只做调用胶水 - ❌ 危险操作:在 default 方法里调用
this.getCache(),而该方法未在接口声明 → 运行时报NoSuchMethodError - ❌ 隐性陷阱:默认方法里抛出
IOException(受检异常),会破坏老实现类的调用链
多个接口冲突时怎么处理
当一个类同时实现 A 和 B 两个接口,而它们都有 default void close(),Java 编译器会直接报错,不让你蒙混过关:
- 必须在实现类中显式
@Override该方法 - 可选择复用某一方实现:
A.super.close(); - 也可混合逻辑:
A.super.close(); B.super.cleanup(); - 若想彻底避免冲突,设计阶段就统一归口,比如让 B 继承 A 并覆盖其 default 方法
怎么确保老代码真能用上新 default 方法
不是写了 default 就自动生效,得满足三个硬性条件:
- 接口编译目标版本 ≥ JDK 8(Maven 中
)1.8 - 运行时 JDK 版本 ≥ 接口编译版本(JDK 7 运行会失败)
- 实现类字节码里没有同签名方法(哪怕只写了个空的
public void run() {},default 就被跳过) - 验证方式:
javap -v YourImpl.class查看方法表,确认没出现新方法名
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











