设计模式之行为模式(二)

(六) state模式
 
State模式在实际使用中比较多,适合"状态的切换".因为我们经常会使用
 
If elseif else 进行状态切换, 如果针对状态的这样判断切换反复出现,
 
我们就要联想到是否可以采取State模式了.
 
这里的状态切换是"开关状态切换" 和" 一般的状态判断"是有一些区别的,
 
"一般的状态判断"也是有 if..elseif结构,例如:
 
if (which==1) state="hello";
else if (which==2) state="hi";
else if (which==3) state="bye";
 
这是一个 "一般的状态判断",state值的不同是根据which变量来决定的,
 
which和state没有关系.如果改成:
 
if (state.euqals("bye")) state="hello";
else if (state.euqals("hello")) state="hi";
else if (state.euqals("hi")) state="bye";
 
这就是 "开关切换状态",是将state的状态从"hello"切换到"hi",
 
再切换到""bye";在切换到"hello",好象
 
一个旋转开关,这种状态改变就可以使用State模式了.
 
如果单纯有上面一种将"hello"-->"hi"-->"bye"-->"hello"这一个方向切换,
 
也不一定需要使用State模式,因为State模式会建立很多子类,复杂化,但是如果又发生另外
 
一个行为:将上面的切换方向反过来切换,或者需要任意切换,就需要State了.
 
如果将上面的切换方向反过来,其实也不一定要使用state.如果切换时行为非常简单,我们
 
可以仍然直接用if else或者switch结构,只有在状态切换时涉及到复杂的具体行为时才真正
 
需要状态切换。
 
例如: 银行帐户, 经常会在Open 状态和Close状态间转换。
 
例如: 经典的TcpConnection, Tcp的状态有创建 侦听 关闭三个,并且反复转换,其创建、侦听、
关闭的具体行为不是简单一两句就能完成的,适合使用State。
 
例如:信箱POP帐号, 会有四种状态, start HaveUsername Authorized quit,每个状态对应的
 
行为应该是比较大的.适合使用State
 
例如:在工具箱挑选不同工具,可以看成在不同工具中切换,适合使用State.如 具体绘图程序,
 
用户可以选择不同工具绘制方框 直线 曲线,这种状态切换可以使用State.
 
(七) strategy模式
 
Strategy是属于设计模式中 对象行为型模式,主要是定义一系列的算法,把这些算法一个个
 
封装成单独的类.Strategy其实是对不同行为的一种封装。如下:
 
ConcreteStrategyC csc = new ConcreteStrategyC();
 
Context c = new Context(csc);
 
c.contextInterface();
 
c.setStrategy(new ConcreteStrategyB());
 
c.contextInterface();
 
ConcreateStrategyC和ConcreteStrategyB都是继承自strategy接口,是不同的行为,
 
在c.contextInterface方法中其实就是调用不同的行为。
 
 _strategy.algorithmInterface();
 
而此处的_strategy就是c.setStrategy传入的。algorithmInterface()即strategy接口
 
的行为接口,是不同的行为类必须要实现的。
 
(八) Mediator模式
 
用一个中介对象来封装一系列关于对象的交互行为.mediator其实是在交互的对象
 
之间起解藕作用。各个对象之间的交互操作非常多;每个对象的行为操作都依赖
 
彼此对方,修改一个对象的行为,同时会涉及到修改很多其他对象的行为,如果使
 
用Mediator模式,可以使各个对象间的耦合松散,只需关心和 Mediator的关系,使多
 
对多的关系变成了一对多的关系,可以降低系统的复杂性,提高可修改扩展性.
 
Mediator模式在事件驱动类应用中比较多,例如界面设计GUI.;聊天,消息传递等,
 
在聊天应用中,需要有一个MessageMediator,专门负责request/reponse之间任务
 
的调节.MVC是J2EE的一个基本模式,View Controller是一种Mediator,它是Jsp和
 
服务器上应用程序间的Mediator.
 
(九) Interprete模式
 
定义语言的文法 ,并且建立一个解释器来解释该语言中的句子.一般用在有编译需求的
 
应用里,用的不多。如下:
 
Context c = new Context(); (1)

AbstractExpression ae = new
 
        NonterminalExpression(new TerminalExpression("hello my friend!"));(2)

ae.interpret(c); (3)
 
AbstractExpression就是表达式的抽象接口,真正的表达式分为终结表达式和非终结两种
 
第(2)行生成了一个表达式,它是一个非终结表达式。传递进取的参数其实是一个终结
 
表达式,当然也可以是非终结表达式再嵌套终结表示式。
 
(3)就是调用表达器的解释行为(充当解释器)来解释ae。
 
c只是一个环境参数,可以传递解释时所用到的一些全局信息。
 
(十) Visitor模式
 
一般通过被访问者的accept方法解耦访问者和被访问者的关系,该模式一般作用于某个对象
 
群中各个对象的操作,JAVA中最常用的就是对集合的访问操作。本来有各种鲜明类型特征
 
的对象一旦放入后,再取出时,这些类型就消失了.那么取出来访问的时候,我们势必要通过
 
if else 和 instanceof来判断取出的对象类型,并进行一系列访问操作。如:
 
Iterator iterator = collection.iterator();
 
while (iterator.hasNext()) {
    
    Object o = iterator.next();
 
    if (o instanceof String)
 
            System.out.println("'"+o.toString()+"'");
 
    else if (o instanceof Float)
    
            System.out.println(o.toString()+"f");
 
    else
            
            System.out.println(o.toString());

}
 
如果访问时的操作过程变的更复杂了,我们势必要修改上述访问的代码,
 
这样给人的感觉很乱。根据面向对象的开闭原则,更改了访问的过程,
 
最好通过增加代码来体现,尽量少修改。
 
从被访问的对象自身的角度来考虑,对象在一个个的容器中,与其在容器外费尽心思判断对象
 
的类型,不如让判断交给对象本身,因为对象自己是知道自己的类型的。这里引入了accept方法。
 
所以我们抽象出了IVisitor和IElement两种东西,所有的被访问者都实现了IElement,其实就是
 
要有accept方法。而所有的访问者都实现了Ivisitor方法。不同的访问者具有各种不同的visit
 
的过程。这样系统的对象层次结构就清晰了。
 
这样对于某个元素的一次访问,代码就可以精简为concreteelement.accept(concretevisitor)。
 
对于不同的访问过程,也只需要实现不同的visitor。更改的代码只要一处。
 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值