意图:让你可以使用不同的业务规则或算法——取决于它们出现的场景。
问题:需要根据发出请求的客户或被处理的数据对算法作出选择。如果你只是拥有一些不发生变化的算法,你就不需要Strategy模式。
解决方案:将算法的选择和算法的实现想分离。让客户可以基于场景做出选择。
参与者和协作者:
1.Strategy规定如何使用不同的算法。
2.ConcreteStrategy实现这些不同的算法。
3.Context通过类型为Strategy的引用使用特定的ConcreteStrategy。Strategy与Context交互实现所选的算法(有时候Strategy必须想Context做查询)。Context将来自Client的请求转发给Strategy。
效果:
1.Strategy模式定义了一系列的算法。
2.switch语句或条件语句得到了避免。
3.你必须以相同的方式调用所有的算法(它们必须拥有相同的接口)ConcreteStrategies与Context之间的交互可能需要在Context中加入getState之类的方法。
实现:让使用算法的类(Context)包含一个抽象类(Strategy),抽象类中有一个抽象类方法指定如何调用算法。每个派生类根据需要实现算法。
注意:
1.如果你希望拥有某些默认行为,这个方法可以不是抽象的。
2.在原型化的Strategy模式中,选择要使用的特定实现的责任是由Client对象来实行的,这提供了Strategy模式的场景。
这里找到了一篇关于 strategy pattern的文章
http://blog.youkuaiyun.com/hfreeman2011/article/details/8502153
感觉没有将factory模式区分开
这里有篇关于这两种模式区别的文章
http://www.dofactory.com/topic/1150/difference-in-strategy-pattern-and-factory-pattern.aspx
factory重在create
strategy重在choose
factory在创建时条件就被确定了
strategy使用是条件可以不断被更改,条件实际上被储存在了context中,
strategy包含了一个factory动作,
比如有一个检索模块
Context context;
context.setName("aa")
context.display()//context内部创建了一个和规则name=aa的对象
context.setSex("male")
context.display()//context内部factory创建了一个和规则 name=aa,sex=male 的对象
如果用factory创建的话,这个context就需要我们自己来维护
ArrayList<HashMap<String,String>> rule = new ArrayList<HashMap<String,String>> ();
rule.put('name','aa')
obj = factory.create(rule)
obj.display()
//注意有没有下面这句的差别
//ArrayList<HashMap<String,String>> rule = new ArrayList<HashMap<String,String>> ();
rule.put('sex','male')
obj = factory.create(rule)
obj.display()
很显然,如果有多个后续条件需要增加的话,context来负责维护就要方便的多,这也是strategy的choose精华所在