早上帮别人写适配器模式的题目时一时之间想不起来,过后花了点时间进行整理,特意记录下来;
参考地址: 适配器模式
场景描述
比如现在有一个支付工具Paypal,通过调用$Paypal->sendPayment($amount)就可以进行支付,但是过了一段时间,这个调用方法名称改变了,或者是改用其它支付工具,显然将每个调用到这个方法的代码都改动一次是不太现实的,这个时候就可以考虑使用适配器模式进行封装;
原始代码
两种支付工具的代码
class Paypal{
public function sendPayment($amount){
echo "pay by Paypal:".$amount."<br>";
}
}
class Skrill{
public function doPayment($amount){
echo "pay by Skrill:".$amount."<br>";
}
}
调用方式:
$paypal = new $Paypal();
$paypal->sendPayment(50);//通过Paypal进行支付
$skrill = new Skrill();
$skrill->doPayment(50);//通过Skrill进行支付
适配器模式
class Adapter implements PayMethod{
private $adapter;
function __construct($adaptee){
$this->adapter = $adaptee;
}
public function pay($amount){
//判断是哪个类
$className = get_class($this->adapter);
if($className == "Paypal"){
$this->adapter->sendPayment($amount);
}elseif ($className == "Skrill") {
$this->adapter->doPayment($amount);
}
}
}
调用方式:
$paypal = new Paypal();
$adapter = new Adapter($paypal);
$adapter->pay(50);//通过paypal付款
$Skrill = new Skrill();
$adapter = new Adapter($Skrill);
$adapter->pay(50);//通过Skrill付款
或者直接将类的声明封装在适配器的内部:
class Adapter implements PayMethod{
private $adapter;
function __construct($className){
if(strtolower($className) == "paypal"){
$this->adapter = new Paypal();
}elseif (strtolower($className) == "skrill") {
$this->adapter = new Skrill();
}
}
public function pay($amount){
//判断是哪个类
$className = get_class($this->adapter);
if($className == "Paypal"){
$this->adapter->sendPayment($amount);
}elseif ($className == "Skrill") {
$this->adapter->doPayment($amount);
}
}
}
调用方式:
$adapter = new Adapter('paypal');
$adapter->pay(50);//通过paypal付款
$adapter = new Adapter('Skrill');
$adapter->pay(50);//通过Skrill付款
运行结果:
pay by Paypal:50
pay by Skrill:50
总结
在这个适配器模式的基础上,以后如果有新的支付方式出现,则直接在Adapter内部添加新的类和方法即可,调用还是统一通过$adapter->pay()进行调用
以上代码可能细节上没有考虑很周全,但是大致是这个思路,仅供参考。
网友评论