多态消除switch-case的本质是将外部类型判断逻辑移交对象自身,通过定义统一接口(如discountpolicy.apply)、为每种类型实现独立类(如vipdiscount)、运行时动态调用,配合工厂或枚举解耦类型识别,使业务代码免于case分支。

多态消除 switch-case 的本质,是把“由外部判断类型再调用逻辑”变成“由对象自己决定怎么执行”。不再让业务方法里堆满 case 分支,而是让每个具体类型封装自己的行为。
提取统一行为,定义接口或抽象类
先观察 switch 中所有 case 在做什么——它们往往是对不同数据做同一类操作,比如计算折扣、解析消息、生成报表、执行支付。把这些共性动作抽成一个接口方法:
- 比如 switch 根据订单类型(NORMAL/VIP/PROMOTION)算价格 → 提取 DiscountPolicy.apply(double amount)
- 比如 switch 根据消息类型(1001/1002/1003)调用不同解码器 → 提取 MessageDecoder.decode(byte[] data)
- 接口只声明“做什么”,不关心“怎么做”,为后续扩展留出空间
为每种情况实现独立类
每个 case 对应一种具体行为,就对应一个实现类:
Java JDK 25 来自 OpenJDK 官方归档,版本为 JDK 25,本条下载地址已指向官方 Windows x64 zip 安装包直链,适合调试旧项目或兼容旧版 Java 运行环境。
- NormalDiscount 实现 apply() 返回 amount × 0.9
- VipDiscount 实现 apply() 返回 amount × 0.7
- PromotionDiscount 实现 apply() 返回 amount × 0.5 + 20
- 新增类型时,只需新增一个类并实现接口,原业务代码完全不动
运行时传入策略对象,直接调用
原来写在 service 方法里的 switch 被彻底移除:
- 旧方式:if (type == VIP) { ... } else if (type == PROMOTION) { ... }
- 新方式:policy.apply(amount) —— JVM 自动找到对应子类方法
- 策略对象可通过工厂、配置、依赖注入等方式获取,调用方只面向接口编程
- 父类引用指向子类实例,如 DiscountPolicy policy = new VipDiscount();
配合枚举或工厂,进一步解耦类型识别
如果仍需从原始类型码(如字符串、数字)获取策略对象,可用枚举或简单工厂封装这一层映射:
- 枚举中每个常量持有一个策略实例:VIP(new VipDiscount())
- 工厂方法根据 type 返回对应实现:DiscountPolicy.of("VIP")
- 这样连“怎么找策略”的逻辑也从主流程剥离,主流程只剩干净的一行调用
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










