高级模块不应取决于低级模块。两者都应取决于抽象。
抽象不应取决于细节。详细信息应取决于抽象。
在下面的示例中,PaymentService
是一个提供付款处理功能的高级模块。这取决于PaymentGateway
抽象,而不是诸如PayPal或Stripe之类的特定实现。这允许在不修改Paymentservice的情况下轻松地交换不同的支付网关。
// High-level module (depends on abstraction)
class PaymentService {
private let paymentGateway: PaymentGateway
init(paymentGateway: PaymentGateway) {
self.paymentGateway = paymentGateway
}
func processPayment(amount: Double) {
// Process payment using the payment gateway
paymentGateway.processPayment(amount: amount)
}
}
// Abstraction (does not depend on details)
protocol PaymentGateway {
func processPayment(amount: Double)
}
// Concrete implementation (depends on abstraction)
class PayPalGateway: PaymentGateway {
func processPayment(amount: Double) {
// Process payment using PayPal API
// Implementation details specific to PayPal
}
}
// Concrete implementation (depends on abstraction)
class StripeGateway: PaymentGateway {
func processPayment(amount: Double) {
// Process payment using Stripe API
// Implementation details specific to Stripe
}
}
PaymentGateway
协议定义了付款网关的所需行为,而混凝土实现(PayPalGateway
和StripeGateway
)取决于抽象。这促进了灵活性,并允许对付款网关实施的未来增加或更改。
通过应用依赖性反转原则,您可以以降低依赖性,提高灵活性并促进更好的代码组织和可维护性的方式设计代码。