抽象方法的核心作用是强制子类实现特定方法,确保多态契约;它必须声明在abstract类中,不可被private/static/final修饰,常与模板方法模式结合,通过final主干逻辑+抽象变化点+钩子方法实现流程复用与灵活扩展。

抽象方法的核心作用,是让基类“留空”一个方法签名,把具体实现的责任明确交给子类。只要子类不是抽象类,就必须填上这个空——编译器会直接拦截未实现的情况,不通过编译。
用 abstract 声明方法,让子类无法绕过
在基类中写一个没有方法体的方法,并加上 abstract 修饰符,同时把整个类也声明为 abstract。例如:
-
protected abstract String generateId();—— 不带大括号,也不写任何逻辑 - 子类若是普通类(非 abstract),不实现它就根本编译不过
- 不能用 private、static 或 final 修饰抽象方法,否则语义冲突
- 推荐用 public 或 protected,兼顾可访问性与封装性
搭配模板方法,固定流程、开放关键环节
光有抽象方法只能卡住入口,真正落地要靠模板方法模式:把不变的主干逻辑写死在 final 方法里,把变化点设为抽象方法,让子类只填空。
- 比如订单创建流程:
validate() → buildOrder() → persist() → notify() - 其中
buildOrder()设为 protected abstract,不同业务子类各自实现构造逻辑 - 模板方法内部可统一处理事务、日志、异常包装等,子类不用重复写
用钩子方法区分“必须”和“可选”
除了强制实现的抽象方法,基类还可提供空的 protected 方法作为扩展点,子类按需重写,不破坏契约。
- 例如:
protected void afterSuccess(Order order) { } - 风控子类重写它加审计日志,普通子类保持默认即可
- 命名建议用
onXXX或afterXXX前缀,语义清晰易识别
注意继承链与初始化安全
抽象方法的约束可以逐层传递,但最终必须由某个具体子类完整履行;同时要避开一个隐蔽陷阱:
- 抽象子类可以不实现父类抽象方法,作为中间设计层(如
Mammal extends Animal) - 具体子类必须实现整条继承链上所有未实现的抽象方法
- 切忌在抽象基类构造器里调用抽象方法——此时子类字段尚未初始化,极易引发空指针











