设计模式之简单工厂模式–利用工厂解耦实例化对象
简单工厂模式
是最常被提起的一个设计模式,他的意思是
利用简单工厂来决定实例化哪个类,而不是由外部程序来决定,把创建对象的操作内聚,解耦到工厂类中。
为什么要使用简单工厂模式
工厂模式除了简单工厂模式
还有工厂方法模式
,抽象工厂模式
。
简单工厂模式有什么好处呢?
简单,非常简单。并且拥有工厂模式的特性,解耦对象的生成。
如果不使用工厂模式,那么对象的创建散落在程序的各个地方,如果需要修改,那么很麻烦。
我们在设计类的时候,为了遵循单一职责原则
,我们应该把类划分的尽可能单一,拿一个实际应用例子来说,支付场景。
支付场景
我们需要在小程序端使用小程序支付,公众号端使用h5支付,pc端使用扫码支付。
后端统一提供支付接口。代码类似下面这样。
1 2 3 4 5 6 7 8 9 10
| function wechatPay() { if (小程序) { } else if (公众号) { } else if (pc) { } }
|
上面的是一个伪代码,这样写不管扩展性,维护性都不好,更不符合单一职责,所以我们应该把支付逻辑抽出来。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40
| interface pay{ function pay(); }
class miniWechatPay implements pay{ function pay() { } }
class jsAPIPay implements pay{ function pay() { } }
class nativePay implements pay{ function pay() { } }
function wechatPay() { if (小程序) { $pay = new miniWechatPay; $pay->pay(); } else if (公众号) { $pay = new jsAPIPay; $pay->pay(); } else if (pc) { $pay = new nativePay; $pay->pay(); } }
|
在if判断里面有重复的地方,都是调用pay
方法,我们可以抽出来。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| function wechatPay() { if (小程序) { $pay = new miniWechatPay; } else if (公众号) { $pay = new jsAPIPay; } else if (pc) { $pay = new nativePay; }
$pay->pay(); }
|
如果接下来我们还要增加刷脸支付等等其他支付怎么办呢,我们只能修改这个方法,这显然是不对的,违反了开闭原则
。
增加支付其实和这个业务逻辑不是一个紧耦合的,我们应该增加他的复用性,如果我们要在其他地方支付呢。应该把实例化这部分也抽出来。就形成了简单工厂类
。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
|
class factory{ function static createPay() { if (小程序) { $pay = new miniWechatPay; } else if (公众号) { $pay = new jsAPIPay; } else if (pc) { $pay = new nativePay; } return $pay; } }
function wechatPay() { $pay = factory::createPay(); $pay->pay(); }
|
这样拆分有什么好处呢?
虽然增加支付的时候依旧需要修改代码,但是只需要修改简单工厂类,而不用修改业务逻辑类,避免了因为修改业务逻辑类而产生的业务逻辑bug。使得实例化对象和具体业务无关。
增加了代码的复用性,维护性,灵活性,测试性等。
代码放在了我的github上面。