简介
"用参数替换查询"是提高方法纯净度的关键重构手法。通过将方法内部的依赖查询改为参数传递,可以消除方法的副作用,增强可测试性并明确方法依赖。
针对的症状(代码坏味道)
- 方法内部访问可变全局状态
- 存在隐藏的数据库/网络查询
- 方法行为依赖其他对象状态
- 需要提高方法可测试性
用参数替换查询的详细步骤
- 识别内部查询
- 查找方法中的对象状态访问
- 标记外部依赖调用点
- 提取为参数
- 将查询结果声明为参数
- 修改方法签名
- 调整调用方
- 在调用处执行查询
- 传入查询结果作为参数
- 验证结果
- 确保参数传递正确
- 保持业务逻辑不变
示例
重构前代码:
class OrderService {
double calculateTotal(Order order) {
double discount = UserSession.getCurrentUser().getDiscountRate();
return order.getAmount() * (1 - discount);
}
}
重构步骤:
-
将折扣率改为参数:
class OrderService { double calculateTotal(Order order, double discountRate) { return order.getAmount() * (1 - discountRate); } } // 调用方 double discount = currentUser.getDiscountRate(); service. calculateTotal(order, discount);
练习
基础练习题
-
简单查询参数化
// 重构前 class ReportGenerator { String generateHeader() { return "Report for " + System.getProperty("user.name"); } }
进阶练习题
-
多依赖参数替换
// 重构前 class PriceCalculator { double calculate(Product product) { double taxRate = TaxTable.getCurrentRate(); double exchangeRate = CurrencyService.getRate("USD"); return product.getCost() * taxRate * exchangeRate; } }
综合拓展练习题
-
对象状态参数化
// 重构前 class ShippingService { double getShippingCost(Order order) { Warehouse warehouse = Warehouse.getNearest(); return warehouse.calculateCost(order.getWeight()); } }
代码审查要点
-
优点:
- 提高方法纯净度
- 明确输入输出关系
- 便于单元测试
-
潜在问题:
- 避免参数列表膨胀
- 注意参数传递性能
- 保持合理抽象层级