java单继承限制可通过组合替代继承来克服:用“has-a”关系(成员变量持有其他类实例)代替“is-a”,配合接口统一调用、委托执行与依赖注入,实现解耦、可扩展与易测试。

Java 的单继承限制不是障碍,而是引导你用更清晰、更可控的方式扩展功能。核心思路是:不靠“我是谁”(is-a),而靠“我拥有谁”(has-a)——也就是用组合代替继承。
用成员变量持有其他类实例
把需要复用的功能封装成独立类,再作为字段放进目标类中。外部类通过调用这些字段的方法来使用功能,而不是靠继承获得。
- 比如想让
ReportGenerator支持导出 PDF 和 Excel,就分别定义PdfExporter和ExcelExporter类 - 在
ReportGenerator中声明private PdfExporter pdfExporter;和private ExcelExporter excelExporter; - 需要导出时,直接调用
pdfExporter.export(report),逻辑解耦、职责分明
配合接口统一调用方式
如果多个组件提供相似能力(如不同格式导出),定义一个通用接口,让各实现类都实现它。这样主类只需面向接口编程,未来新增格式也不用改主逻辑。
你接手一个需求时,是不是经常这样:"改一个小字段 → 结果把不相关的代码也改了"、"需求说得很模糊 → 做着做着发现跑偏了"、"数据库加个字段 → 上线才发现漏了数据兼容"、"做了个新功能 → 一个月后自己都忘了当时怎么设计的"、"写到一半被中断 → 再回来不知道从哪继续";这个 Skill 就是专门解决这些问题的。 它会自动探测你的项目环境(JDK、Spring Boot、ORM、数据库、前端框架),记在
- 定义
Exporter接口,含export(Report report)方法 -
PdfExporter和ExcelExporter都实现该接口 -
ReportGenerator持有private Exporter exporter;,运行时可动态替换
委托调用 + 灵活装配
组合的关键在于“委托”——主类不自己实现细节,而是把任务交给内部对象。这带来两大好处:一是可运行时切换行为(如换用不同压缩算法),二是便于单元测试(可注入模拟对象)。
- 构造器或 setter 中传入具体实现,支持依赖注入
- 避免在主类里写大量
if-else判断类型,而是由具体组件自行处理 - 例如日志功能:主业务类持有
Logger接口引用,实际用FileLogger还是RemoteLogger完全可配
结合内部类做轻量级增强
当某段逻辑只在当前类上下文中使用,又需访问私有成员时,非静态内部类是个好选择。它能自然持有外部类引用,同时封装专属行为,避免暴露多余 public 方法。
- 比如网络请求类中,定义一个内部类
RetryPolicy处理重试逻辑 - 该内部类可直接读写外部类的
timeout、maxRetries等字段 - 对外不暴露
RetryPolicy类型,仅通过外部类方法间接使用
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










