做网站和开发app有什么不同,做网站销售怎么样,数字营销策划公司,网站建设的重要SOLID原则。
依赖倒置原则#xff08;DIP#xff09;的核心是高层模块不应该依赖于低层模块#xff0c;二者都应该依赖于抽象#xff08;接口或抽象类#xff09;
例如#xff0c;随着业务的发展#xff0c;订单总金额的计算规则可能需要根据不同的客户类型或促销活动…SOLID原则。
依赖倒置原则DIP的核心是高层模块不应该依赖于低层模块二者都应该依赖于抽象接口或抽象类
例如随着业务的发展订单总金额的计算规则可能需要根据不同的客户类型或促销活动进行调整。如果最初没有使用接口来抽象计算逻辑那么可能需要直接修改具体的业务代码这会增加代码的修改风险和维护成本。而使用接口可以方便地实现不同的计算策略通过依赖注入等方式进行切换提高系统的灵活性和可扩展性。 接下来我们逐步优化把他变得满足SRP和OCP、DIP原则了。
循环累加
public class Order {private double[] productPrices;public Order(double[] productPrices) {this.productPrices productPrices;}// 计算订单总金额的方法public double calculateTotalAmount() {double total 0;for (double price : productPrices) {total price;}return total;}
}当业务发展需要根据不同客户类型比如普通客户、VIP 客户和促销活动比如满减、折扣来调整订单总金额的计算规则时就需要直接修改 calculateTotalAmount 方法的代码。例如VIP 客户享受 9 折优惠满 100 减 20 的促销活动代码修改如下
public class Order {private double[] productPrices;private String customerType;public Order(double[] productPrices, String customerType) {this.productPrices productPrices;this.customerType customerType;}// 计算订单总金额的方法修改后变得复杂public double calculateTotalAmount() {double total 0;for (double price : productPrices) {total price;}if (VIP.equals(customerType)) {total * 0.9;}if (total 100) {total - 20;}return total;}
}这种直接修改的方式随着业务规则的不断增加和变化代码会变得越来越复杂和难以维护修改一处可能会影响到其他部分的逻辑增加了出错的风险。
抽象工厂
我们发现订单类和计算金额的修改原因、修改速率不一样根据SRP原则利用抽象工厂模式把他抽出来如下。
// 订单类
public class Order {private double[] productPrices;private String customerType;public Order(double[] productPrices, String customerType) {this.productPrices productPrices;this.customerType customerType;}// 计算总金额依赖工厂类public double calculateTotalAmount() {return OrderTotalCalculatorFactory.calculateTotal(productPrices, customerType);}
}// 订单总金额计算工厂类
public class OrderTotalCalculatorFactory {public static double calculateTotal(double[] productPrices, String customerType) {if (Regular.equals(customerType)) {double total 0;for (double price : productPrices) {total price;}return total;} else if (VIP.equals(customerType)) {double total 0;for (double price : productPrices) {total price;}total * 0.9;return total;} else {double total 0;for (double price : productPrices) {total price;}if (total 100) {total - 20;}return total;}}
}引入抽象类
如果再有新的计费类型时我们需要修改OrderTotalCalculatorFactory 再添加一个if-else然后在里面写代码违反了OCP原则。所以我们不把具体代码写到OrderTotalCalculatorFactory 里而是再抽一层可以是接口也可以不是。这样不是说没有改动但是改动点小了。是扩展本类而不是修改 但是为了专业把相同的抽出来作为上层我们没有理由不写成接口。 此外如果再想加一个过期时间校验功能我们的优惠、会员等都是有时间的先校验然后再计算金额。这个时候就体现出接口的好处来了。
这样就是所谓的DIP了由原来的order订单依赖于金额计算现在加了一个接口二者都依赖于这个接口了。
// 订单总金额计算策略接口
public interface OrderTotalCalculator {double calculateTotal(double[] productPrices);
}// 普通客户计算策略实现类
public class RegularCustomerCalculator implements OrderTotalCalculator {Overridepublic double calculateTotal(double[] productPrices) {double total 0;for (double price : productPrices) {total price;}return total;}
}// VIP客户计算策略实现类
public class VIPCustomerCalculator implements OrderTotalCalculator {Overridepublic double calculateTotal(double[] productPrices) {double total 0;for (double price : productPrices) {total price;}total * 0.9;return total;}
}// 工厂类
public class OrderTotalCalculatorFactory {public static OrderTotalCalculator createCalculator(String customerType) {if (Regular.equals(customerType)) {return new RegularCustomerCalculator();} else if (VIP.equals(customerType)) {return new VIPCustomerCalculator();} // 目前只有这两种情况后续可扩展return null;}
}// 组合优于继承
public class Order {private double[] productPrices;private String customerType;private OrderTotalCalculator calculator;public Order(double[] productPrices, String customerType) {this.productPrices productPrices;this.customerType customerType;this.calculator OrderTotalCalculatorFactory.createCalculator(customerType);}public double calculateTotalAmount() {return calculator.calculateTotal(productPrices);}
}