RSS订阅欢迎来到Java程序员学习天地!
你的位置:首页 » Java开发中的23种模式(五)

Java开发中的23种模式(五)

18、命令模式(Command)

命令模式很好理解,举个例子,司令员下令让士兵去干件事情,从整个事情的角度来考虑,司令员的作用是,发出口令,口令经过传递,传到了士兵耳朵里,士兵去执行。这个过程好在,三者相互解耦,任何一方都不用去依赖其他人,只需要做好自己的事儿就行,司令员要的是结果,不会去关注到底士兵是怎么实现的。我们看看关系图:


Invoker是调用者(司令员),Receiver是被调用者(士兵),MyCommand是命令,实现了Command接口,持有接收对象,看实现代码:

[java] view plaincopy

  1. public interface Command {  

  2.     public void exe();  

  3. }  

[java] view plaincopy

  1. public class MyCommand implements Command {  

  2.   

  3.     private Receiver receiver;  

  4.       

  5.     public MyCommand(Receiver receiver) {  

  6.         this.receiver = receiver;  

  7.     }  

  8.   

  9.     @Override  

  10.     public void exe() {  

  11.         receiver.action();  

  12.     }  

  13. }  

[java] view plaincopy

  1. public class Receiver {  

  2.     public void action(){  

  3.         System.out.println("command received!");  

  4.     }  

  5. }  

[java] view plaincopy

  1. public class Invoker {  

  2.       

  3.     private Command command;  

  4.       

  5.     public Invoker(Command command) {  

  6.         this.command = command;  

  7.     }  

  8.   

  9.     public void action(){  

  10.         command.exe();  

  11.     }  

  12. }  

[java] view plaincopy

  1. public class Test {  

  2.   

  3.     public static void main(String[] args) {  

  4.         Receiver receiver = new Receiver();  

  5.         Command cmd = new MyCommand(receiver);  

  6.         Invoker invoker = new Invoker(cmd);  

  7.         invoker.action();  

  8.     }  

  9. }  

输出:command received!

这个很哈理解,命令模式的目的就是达到命令的发出者和执行者之间解耦,实现请求和执行分开,熟悉Struts的同学应该知道,Struts其实就是一种将请求和呈现分离的技术,其中必然涉及命令模式的思想!

其实每个设计模式都是很重要的一种思想,看上去很熟,其实是因为我们在学到的东西中都有涉及,尽管有时我们并不知道,其实在Java本身的设计之中处处都有体现,像AWT、JDBC、集合类、IO管道或者是Web框架,里面设计模式无处不在。因为我们篇幅有限,很难讲每一个设计模式都讲的很详细,不过我会尽我所能,尽量在有限的空间和篇幅内,把意思写清楚了,更好让大家明白。本章不出意外的话,应该是设计模式最后一讲了,首先还是上一下上篇开头的那个图:


本章讲讲第三类和第四类。

19、备忘录模式(Memento)

主要目的是保存一个对象的某个状态,以便在适当的时候恢复对象,个人觉得叫备份模式更形象些,通俗的讲下:假设有原始类A,A中有各种属性,A可以决定需要备份的属性,备忘录类B是用来存储A的一些内部状态,类C呢,就是一个用来存储备忘录的,且只能存储,不能修改等操作。做个图来分析一下:


Original类是原始类,里面有需要保存的属性value及创建一个备忘录类,用来保存value值。Memento类是备忘录类,Storage类是存储备忘录的类,持有Memento类的实例,该模式很好理解。直接看源码:

[java] view plaincopy

  1. public class Original {  

  2.       

  3.     private String value;  

  4.       

  5.     public String getValue() {  

  6.         return value;  

  7.     }  

  8.   

  9.     public void setValue(String value) {  

  10.         this.value = value;  

  11.     }  

  12.   

  13.     public Original(String value) {  

  14.         this.value = value;  

  15.     }  

  16.   

  17.     public Memento createMemento(){  

  18.         return new Memento(value);  

  19.     }  

  20.       

  21.     public void restoreMemento(Memento memento){  

  22.         this.value = memento.getValue();  

  23.     }  

  24. }  

[java] view plaincopy

  1. public class Memento {  

  2.       

  3.     private String value;  

  4.   

  5.     public Memento(String value) {  

  6.         this.value = value;  

  7.     }  

  8.   

  9.     public String getValue() {  

  10.         return value;  

  11.     }  

  12.   

  13.     public void setValue(String value) {  

  14.         this.value = value;  

  15.     }  

  16. }  

[java] view plaincopy

  1. public class Storage {  

  2.       

  3.     private Memento memento;  

  4.       

  5.     public Storage(Memento memento) {  

  6.         this.memento = memento;  

  7.     }  

  8.   

  9.     public Memento getMemento() {  

  10.         return memento;  

  11.     }  

  12.   

  13.     public void setMemento(Memento memento) {  

  14.         this.memento = memento;  

  15.     }  

  16. }  

测试类:

[java] view plaincopy

  1. public class Test {  

  2.   

  3.     public static void main(String[] args) {  

  4.           

  5.         // 创建原始类  

  6.         Original origi = new Original("egg");  

  7.   

  8.         // 创建备忘录  

  9.         Storage storage = new Storage(origi.createMemento());  

  10.   

  11.         // 修改原始类的状态  

  12.         System.out.println("初始化状态为:" + origi.getValue());  

  13.         origi.setValue("niu");  

  14.         System.out.println("修改后的状态为:" + origi.getValue());  

  15.   

  16.         // 回复原始类的状态  

  17.         origi.restoreMemento(storage.getMemento());  

  18.         System.out.println("恢复后的状态为:" + origi.getValue());  

  19.     }  

  20. }  

输出:

初始化状态为:egg
修改后的状态为:niu
恢复后的状态为:egg

简单描述下:新建原始类时,value被初始化为egg,后经过修改,将value的值置为niu,最后倒数第二行进行恢复状态,结果成功恢复了。其实我觉得这个模式叫“备份-恢复”模式最形象。

20、状态模式(State)

核心思想就是:当对象的状态改变时,同时改变其行为,很好理解!就拿QQ来说,有几种状态,在线、隐身、忙碌等,每个状态对应不同的操作,而且你的好友也能看到你的状态,所以,状态模式就两点:1、可以通过改变状态来获得不同的行为。2、你的好友能同时看到你的变化。看图:


State类是个状态类,Context类可以实现切换,我们来看看代码:

 

[java] view plaincopy

  1. package com.xtfggef.dp.state;  

  2.   

  3. /** 

  4.  * 状态类的核心类 

  5.  * 2012-12-1 

  6.  * @author erqing 

  7.  * 

  8.  */  

  9. public class State {  

  10.       

  11.     private String value;  

  12.       

  13.     public String getValue() {  

  14.         return value;  

  15.     }  

  16.   

  17.     public void setValue(String value) {  

  18.         this.value = value;  

  19.     }  

  20.   

  21.     public void method1(){  

  22.         System.out.println("execute the first opt!");  

  23.     }  

  24.       

  25.     public void method2(){  

  26.         System.out.println("execute the second opt!");  

  27.     }  

  28. }  

[java] view plaincopy

  1. package com.xtfggef.dp.state;  

  2.   

  3. /** 

  4.  * 状态模式的切换类   2012-12-1 

  5.  * @author erqing 

  6.  *  

  7.  */  

  8. public class Context {  

  9.   

  10.     private State state;  

  11.   

  12.     public Context(State state) {  

  13.         this.state = state;  

  14.     }  

  15.   

  16.     public State getState() {  

  17.         return state;  

  18.     }  

  19.   

  20.     public void setState(State state) {  

  21.         this.state = state;  

  22.     }  

  23.   

  24.     public void method() {  

  25.         if (state.getValue().equals("state1")) {  

  26.             state.method1();  

  27.         } else if (state.getValue().equals("state2")) {  

  28.             state.method2();  

  29.         }  

  30.     }  

  31. }  

测试类:

 

 

[java] view plaincopy

  1. public class Test {  

  2.   

  3.     public static void main(String[] args) {  

  4.           

  5.         State state = new State();  

  6.         Context context = new Context(state);  

  7.           

  8.         //设置第一种状态  

  9.         state.setValue("state1");  

  10.         context.method();  

  11.           

  12.         //设置第二种状态  

  13.         state.setValue("state2");  

  14.         context.method();  

  15.     }  

  16. }  

输出:

 

execute the first opt!
execute the second opt!

根据这个特性,状态模式在日常开发中用的挺多的,尤其是做网站的时候,我们有时希望根据对象的某一属性,区别开他们的一些功能,比如说简单的权限控制等。


额 本文暂时没人评论 来添加一个吧

发表评论

必填

选填

选填

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

控制面板
您好,欢迎到访网站!
随机文章
热门文章
热评文章
最近发表