在策略模式(Strategy Pattern)中,一个类的行为或其算法可以在运行时更改。这种类型的设计模式属于行为型模式。其实现原理是定义一系列的算法,将他们一个个封装起来,并且是他们可以互相替换,这样避免了使用 if … else 语句所带来的复杂度和维护成。如果一个系统里有许多的类,而这些类之间的区别仅在于它们行为的不同,系统也需要动态的选择几种算法中的一种,这时使用策略模式是一种很好的解决方案。
下面的示例演示两个数之间的“加减乘除”运算,在工厂模式一节中,我们使用的是工厂模式实现这种计算,其是根据传入的不同参数分别生成不同的类实例。而本次示例使用策略模式来实现这种数学运算。代码如下:
<?php
//定义接口
interface Calc{
public function getValue($num1,$num2);
}
//四个类表示四种可供选择的策略
class AddStrategy implements Calc {
public function getValue($m,$n){
echo $m + $n;
}
}
class SubStrategy implements Calc {
public function getValue($m,$n){
echo $m - $n;
}
}
class MulStratygy implements Calc {
public function getValue($m,$n){
echo $m * $n;
}
}
class DivStrategy implements Calc {
public function getValue($m,$n){
try {
if($n == 0) {
throw new Exception("除数不能为0");
} else {
echo $m/$n;
}
} catch (Exception $e) {
echo "错误信息:" . $e->getMessage();
}
}
}
class CalcContext{
private $_strategy = null;
public function __construct(Calc $select){
$this->_strategy = $select;
}
//设置使用的策略类
public function setCalc(Calc $select){
return $this->_strategy = $select;
}
public function calcResult($m,$n){
$this->_strategy->getValue($m,$n);
}
}
$result = new CalcContext(new AddStrategy());
$result->calcResult(10,2);
// 切换不同策略
$result->setCalc(new DivStrategy());
$result->calcResult(10,2);
?>
执行以上程序在浏览器输出结果为:12 5 。
我们使用策略模式和工厂模式都实现了这种功能,两者的区别是,工厂模式关注对象的创建,提供创建对象的接口,它是创建型的设计模式,它接受指令,创建出符合要求的实例;而策略模式是行为型的设计模式,它接受已经创建好的实例,实现不同的行为。
原文地址:http://chenxiaolong.blog.51cto.com/8786841/1791873