多折扣类实现是否存在冗余?代码合法性与优化咨询
代码合法性判断
你的代码语法完全合法,能够正常编译运行,但存在一处访问控制的可优化点:所有折扣实现类的访问修饰符默认是包私有(package-private),如果需要在当前包外调用这些类,建议将它们的访问修饰符改为public。
优化方案(减少冗余、提升效率)
结合你后续要接收三类折扣输入的场景,以下是针对性的优化方向:
1. 无状态折扣类改用单例/枚举实现
StudentDiscount和SeniorCitizenDiscount是无状态的(没有成员变量,折扣逻辑固定),每次创建新实例属于不必要的开销,用枚举或单例可以避免重复对象创建:
枚举实现(推荐,天然单例+线程安全)
public interface Discount { double applyDiscount(double amount); } enum FixedDiscounts implements Discount { STUDENT_DISCOUNT { @Override public double applyDiscount(double amount) { return amount * 0.9; } }, SENIOR_CITIZEN_DISCOUNT { @Override public double applyDiscount(double amount) { return amount * 0.8; } }; } public class BulkOrderDiscount implements Discount { private final int threshold; private final double discountRate; // 构造器私有化,用静态工厂方法创建实例 private BulkOrderDiscount(int threshold, double discountRate) { this.threshold = threshold; this.discountRate = discountRate; } public static BulkOrderDiscount of(int threshold, double discountRate) { // 可在此添加参数合法性校验,比如阈值不能为负、折扣率需在0-1之间 if (threshold < 0 || discountRate < 0 || discountRate > 1) { throw new IllegalArgumentException("非法的批量折扣参数"); } return new BulkOrderDiscount(threshold, discountRate); } @Override public double applyDiscount(double amount) { return amount >= threshold ? amount * (1 - discountRate) : amount; } }
2. 提取通用逻辑,避免代码重复
如果后续可能新增更多固定折扣类,可以把固定折扣的逻辑抽象成基础类,减少重复代码:
public abstract class FixedRateDiscount implements Discount { protected final double rate; protected FixedRateDiscount(double rate) { this.rate = rate; } @Override public double applyDiscount(double amount) { return amount * rate; } } // 学生折扣类 public class StudentDiscount extends FixedRateDiscount { private static final StudentDiscount INSTANCE = new StudentDiscount(); private StudentDiscount() { super(0.9); } public static StudentDiscount getInstance() { return INSTANCE; } } // 老年人类似实现 public class SeniorCitizenDiscount extends FixedRateDiscount { private static final SeniorCitizenDiscount INSTANCE = new SeniorCitizenDiscount(); private SeniorCitizenDiscount() { super(0.8); } public static SeniorCitizenDiscount getInstance() { return INSTANCE; } }
3. 用工厂模式适配输入场景
针对你需要接收三类输入的需求,用工厂模式可以统一创建Discount实例,避免业务代码中出现大量if-else判断:
public class DiscountFactory { public static Discount createDiscount(String type, Map<String, Object> params) { return switch (type.toLowerCase()) { case "student discount" -> FixedDiscounts.STUDENT_DISCOUNT; case "senior discount" -> FixedDiscounts.SENIOR_CITIZEN_DISCOUNT; case "bulk discount" -> { if (params == null || !params.containsKey("threshold") || !params.containsKey("discountRate")) { throw new IllegalArgumentException("批量折扣缺少必要参数"); } int threshold = (int) params.get("threshold"); double discountRate = (double) params.get("discountRate"); yield BulkOrderDiscount.of(threshold, discountRate); } default -> throw new IllegalArgumentException("不支持的折扣类型: " + type); }; } }
使用示例:
// 创建学生折扣 Discount studentDiscount = DiscountFactory.createDiscount("student discount", null); // 创建批量折扣 Map<String, Object> bulkParams = new HashMap<>(); bulkParams.put("threshold", 1000); bulkParams.put("discountRate", 0.15); Discount bulkDiscount = DiscountFactory.createDiscount("bulk discount", bulkParams);
额外优化细节
- 将
BulkOrderDiscount的成员变量设为final,保证对象不可变性,提升线程安全性; - 在工厂方法和批量折扣构造器中添加参数合法性校验,提前拦截非法输入,避免运行时错误。
内容的提问来源于stack exchange,提问作者ineedmoney
相关产品推荐
相关产品推荐

