Java方法封装案例如何优化

wen java案例 22

Java方法封装优化案例

原始版本 - 未优化的长方法

public class OrderService {
    public void processOrder(Order order) {
        // 验证订单
        if (order == null) {
            throw new IllegalArgumentException("订单不能为空");
        }
        if (order.getItems() == null || order.getItems().isEmpty()) {
            throw new IllegalArgumentException("订单项不能为空");
        }
        if (order.getTotalAmount() <= 0) {
            throw new IllegalArgumentException("订单金额必须大于0");
        }
        // 计算折扣
        double discount = 0;
        if (order.getTotalAmount() > 1000) {
            discount = 0.1;
        } else if (order.getTotalAmount() > 500) {
            discount = 0.05;
        }
        double finalAmount = order.getTotalAmount() * (1 - discount);
        // 更新库存
        for (OrderItem item : order.getItems()) {
            Product product = productRepository.findById(item.getProductId());
            if (product.getStock() < item.getQuantity()) {
                throw new RuntimeException("库存不足: " + product.getName());
            }
            product.setStock(product.getStock() - item.getQuantity());
            productRepository.save(product);
        }
        // 发送通知
        String message = String.format("订单 %s 已处理,金额: %.2f", 
                                        order.getOrderId(), finalAmount);
        notificationService.send(order.getUserId(), message);
        // 保存订单
        order.setStatus("PROCESSED");
        orderRepository.save(order);
    }
}

优化版本 - 单一职责原则

@Service
public class OrderService {
    private final OrderValidator orderValidator;
    private final DiscountCalculator discountCalculator;
    private final InventoryManager inventoryManager;
    private final NotificationService notificationService;
    private final OrderRepository orderRepository;
    public OrderService(OrderValidator orderValidator,
                       DiscountCalculator discountCalculator,
                       InventoryManager inventoryManager,
                       NotificationService notificationService,
                       OrderRepository orderRepository) {
        this.orderValidator = orderValidator;
        this.discountCalculator = discountCalculator;
        this.inventoryManager = inventoryManager;
        this.notificationService = notificationService;
        this.orderRepository = orderRepository;
    }
    public void processOrder(Order order) {
        // 1. 校验订单
        orderValidator.validate(order);
        // 2. 计算折扣和最终金额
        double finalAmount = discountCalculator.calculateFinalAmount(order);
        // 3. 更新库存
        inventoryManager.updateStock(order.getItems());
        // 4. 发送通知
        notificationService.sendOrderProcessedNotification(order, finalAmount);
        // 5. 保存订单
        saveProcessedOrder(order, finalAmount);
    }
    private void saveProcessedOrder(Order order, double finalAmount) {
        order.setFinalAmount(finalAmount);
        order.setStatus("PROCESSED");
        orderRepository.save(order);
    }
}

各个职责分离的类

// 订单校验器
@Component
public class OrderValidator {
    public void validate(Order order) {
        validateNotNull(order);
        validateItems(order.getItems());
        validateTotalAmount(order.getTotalAmount());
    }
    private void validateNotNull(Order order) {
        if (order == null) {
            throw new IllegalArgumentException("订单不能为空");
        }
    }
    private void validateItems(List<OrderItem> items) {
        if (items == null || items.isEmpty()) {
            throw new IllegalArgumentException("订单项不能为空");
        }
        // 可以继续验证每个商品
        items.forEach(this::validateItem);
    }
    private void validateItem(OrderItem item) {
        if (item.getQuantity() <= 0) {
            throw new IllegalArgumentException("商品数量必须大于0");
        }
    }
    private void validateTotalAmount(double amount) {
        if (amount <= 0) {
            throw new IllegalArgumentException("订单金额必须大于0");
        }
    }
}
// 折扣计算器
@Component
public class DiscountCalculator {
    private static final double HIGH_DISCOUNT_THRESHOLD = 1000;
    private static final double MID_DISCOUNT_THRESHOLD = 500;
    private static final double HIGH_DISCOUNT_RATE = 0.1;
    private static final double MID_DISCOUNT_RATE = 0.05;
    public double calculateFinalAmount(Order order) {
        double discount = getDiscountRate(order.getTotalAmount());
        return order.getTotalAmount() * (1 - discount);
    }
    private double getDiscountRate(double totalAmount) {
        if (totalAmount > HIGH_DISCOUNT_THRESHOLD) {
            return HIGH_DISCOUNT_RATE;
        }
        if (totalAmount > MID_DISCOUNT_THRESHOLD) {
            return MID_DISCOUNT_RATE;
        }
        return 0;
    }
}
// 库存管理器
@Component
public class InventoryManager {
    private final ProductRepository productRepository;
    public InventoryManager(ProductRepository productRepository) {
        this.productRepository = productRepository;
    }
    public void updateStock(List<OrderItem> items) {
        items.forEach(this::updateSingleItemStock);
    }
    private void updateSingleItemStock(OrderItem item) {
        Product product = findProduct(item.getProductId());
        validateStock(product, item.getQuantity());
        product.setStock(product.getStock() - item.getQuantity());
        productRepository.save(product);
    }
    private Product findProduct(String productId) {
        return productRepository.findById(productId)
            .orElseThrow(() -> new RuntimeException("商品不存在: " + productId));
    }
    private void validateStock(Product product, int requiredQuantity) {
        if (product.getStock() < requiredQuantity) {
            throw new RuntimeException("库存不足: " + product.getName());
        }
    }
}
// 通知服务
@Component
public class NotificationService {
    public void sendOrderProcessedNotification(Order order, double finalAmount) {
        String message = buildNotificationMessage(order, finalAmount);
        sendNotification(order.getUserId(), message);
    }
    private String buildNotificationMessage(Order order, double finalAmount) {
        return String.format("订单 %s 已处理,金额: %.2f", 
                           order.getOrderId(), finalAmount);
    }
    private void sendNotification(String userId, String message) {
        // 实际发送逻辑
        System.out.println("发送通知给用户 " + userId + ": " + message);
    }
}

策略模式优化折扣计算

// 折扣策略接口
public interface DiscountStrategy {
    double calculateDiscount(double totalAmount);
    boolean supports(double totalAmount);
}
// 高级折扣策略
@Component
public class HighDiscountStrategy implements DiscountStrategy {
    private static final double THRESHOLD = 1000;
    private static final double DISCOUNT_RATE = 0.1;
    @Override
    public double calculateDiscount(double totalAmount) {
        return totalAmount * DISCOUNT_RATE;
    }
    @Override
    public boolean supports(double totalAmount) {
        return totalAmount > THRESHOLD;
    }
}
// 中级折扣策略
@Component
public class MidDiscountStrategy implements DiscountStrategy {
    private static final double THRESHOLD = 500;
    private static final double DISCOUNT_RATE = 0.05;
    @Override
    public double calculateDiscount(double totalAmount) {
        return totalAmount * DISCOUNT_RATE;
    }
    @Override
    public boolean supports(double totalAmount) {
        return totalAmount > THRESHOLD && totalAmount <= 1000;
    }
}
// 优化后的折扣计算器
@Component
public class AdvancedDiscountCalculator {
    private final List<DiscountStrategy> strategies;
    public AdvancedDiscountCalculator(List<DiscountStrategy> strategies) {
        this.strategies = strategies;
    }
    public double calculateFinalAmount(Order order) {
        double totalAmount = order.getTotalAmount();
        double discount = findApplicableStrategy(totalAmount)
            .map(strategy -> strategy.calculateDiscount(totalAmount))
            .orElse(0.0);
        return totalAmount - discount;
    }
    private Optional<DiscountStrategy> findApplicableStrategy(double totalAmount) {
        return strategies.stream()
            .filter(strategy -> strategy.supports(totalAmount))
            .findFirst();
    }
}

单元测试示例

@SpringBootTest
class OrderServiceTest {
    @MockBean
    private OrderValidator orderValidator;
    @MockBean
    private DiscountCalculator discountCalculator;
    @MockBean
    private InventoryManager inventoryManager;
    @MockBean
    private NotificationService notificationService;
    @MockBean
    private OrderRepository orderRepository;
    @Autowired
    private OrderService orderService;
    @Test
    void testProcessOrder() {
        // 准备测试数据
        Order order = createTestOrder();
        // 设置mock行为
        Mockito.doNothing().when(orderValidator).validate(any(Order.class));
        Mockito.when(discountCalculator.calculateFinalAmount(any(Order.class)))
            .thenReturn(1000.0);
        Mockito.doNothing().when(inventoryManager).updateStock(anyList());
        Mockito.doNothing().when(notificationService)
            .sendOrderProcessedNotification(any(Order.class), anyDouble());
        // 执行测试
        orderService.processOrder(order);
        // 验证
        Mockito.verify(orderRepository).save(any(Order.class));
        assertEquals("PROCESSED", order.getStatus());
        assertEquals(1000.0, order.getFinalAmount(), 0.01);
    }
}

优化总结

优化前 优化后 优点
单个长方法 多个职责分离的类 可维护性提高
硬编码业务逻辑 策略模式 易于扩展新折扣规则
直接依赖具体实现 依赖注入 便于测试和替换
无单元测试 完善的单元测试 保证代码质量
魔法数值 常量定义 代码更清晰

这种优化方式遵循了SOLID原则,特别是单一职责原则和开闭原则,使代码更加健壮、可测试和可维护。

Java方法封装案例如何优化

抱歉,评论功能暂时关闭!