ToB企服应用市场:ToB评测及商务社交产业平台

标题: 命令模式 [打印本页]

作者: tsx81429    时间: 2023-10-9 21:55
标题: 命令模式
命令模式

案例引入

要求

基本介绍

原理类图


类图说明

命令模式实现案例

案例uml类图


代码
  1. /**
  2. * @author 长名06
  3. * @version 1.0
  4. */
  5. public interface Command {
  6.     public void execute();
  7.     public void undo();
  8. }
  9. /**
  10. * @author 长名06
  11. * @version 1.0
  12. */
  13. public class LightOffCommand implements Command{
  14.     private LightReceiver receiver;
  15.     public LightOffCommand(LightReceiver receiver){
  16.         this.receiver = receiver;
  17.     }
  18.     @Override
  19.     public void execute() {
  20.         receiver.off();
  21.     }
  22.     @Override
  23.     public void undo() {
  24.         receiver.on();
  25.     }
  26. }
  27. /**
  28. * @author 长名06
  29. * @version 1.0
  30. */
  31. public class LightOnCommand implements Command{
  32.     //组合实际命令的执行者(命令接收者)
  33.     private LightReceiver receiver;
  34.     public LightOnCommand(LightReceiver receiver){
  35.         this.receiver = receiver;
  36.     }
  37.     @Override
  38.     public void execute() {
  39.         receiver.on();
  40.     }
  41.     @Override
  42.     public void undo() {
  43.         receiver.off();
  44.     }
  45. }
  46. /**
  47. * 没有任何命令,即空执行 用于初始化每个按钮 调用空命令时,对象什么都不做
  48. * 其实这也是一种设计模式,可以省掉空判断
  49. * @author 长名06
  50. * @version 1.0
  51. */
  52. public class NoCommand implements Command{
  53.     @Override
  54.     public void execute() {
  55.     }
  56.     @Override
  57.     public void undo() {
  58.     }
  59. }
  60. /**
  61. * @author 长名06
  62. * @version 1.0
  63. */
  64. public class TVOffCommand implements Command{
  65.     private TVReceiver tvReceiver;
  66.     public TVOffCommand(TVReceiver tvReceiver){
  67.         this.tvReceiver = tvReceiver;
  68.     }
  69.     @Override
  70.     public void execute() {
  71.         tvReceiver.off();
  72.     }
  73.     @Override
  74.     public void undo() {
  75.         tvReceiver.on();
  76.     }
  77. }
  78. /**
  79. * @author 长名06
  80. * @version 1.0
  81. */
  82. public class TVOnCommand implements Command{
  83.     private TVReceiver tvReceiver;
  84.     public TVOnCommand(TVReceiver tvReceiver){
  85.         this.tvReceiver = tvReceiver;
  86.     }
  87.     @Override
  88.     public void execute() {
  89.         tvReceiver.on();
  90.     }
  91.     @Override
  92.     public void undo() {
  93.         tvReceiver.off();
  94.     }
  95. }
  96. /**
  97. * @author 长名06
  98. * @version 1.0
  99. */
  100. public class LightReceiver {
  101.     public void on(){
  102.         System.out.println("电灯打开");
  103.     }
  104.     public void off(){
  105.         System.out.println("电灯关闭");
  106.     }
  107. }
  108. /**
  109. * @author 长名06
  110. * @version 1.0
  111. */
  112. public class TVReceiver {
  113.     public void on(){
  114.         System.out.println("电视打开了");
  115.     }
  116.     public void off(){
  117.         System.out.println("电视关闭了");
  118.     }
  119. }
  120. /**
  121. * @author 长名06
  122. * @version 1.0
  123. */
  124. public class RemoterController {
  125.     //开按钮命令数组
  126.     private Command[] onCommands;
  127.     //关按钮命令数组
  128.     private Command[] offCommands;
  129.     //执行撤销命令按钮
  130.     private Command undoCommand;
  131.     /**
  132.      * 构造方法,传入指令数组的长度,以及数组中初始的指令类型
  133.      */
  134.     public RemoterController(){
  135.         //先赋值,后使用
  136.         onCommands = new Command[5];
  137.         offCommands = new Command[5];
  138.         for (int i = 0; i < 5; i++) {
  139.             onCommands[i] = new NoCommand();
  140.             offCommands[i] = new NoCommand();
  141.         }
  142.     }
  143.     /**
  144.      * 根据数组下标设置特定打开指令
  145.      * @param i
  146.      */
  147.     public void setCommand(int i,Command onCommand,Command offCommand){
  148.         if(i < 0 || i >= onCommands.length){
  149.             throw new IndexOutOfBoundsException();
  150.         }
  151.         onCommands[i] = onCommand;
  152.         offCommands[i] = offCommand;
  153.     }
  154.     public void onButtonWasPushed(int no){
  155.         //找到按下的开按钮对应的命令,并执行命令
  156.         onCommands[no].execute();
  157.         //记录这次操作,用于撤销
  158.         undoCommand = onCommands[no];
  159.     }
  160.     public void offButtonWasPushed(int no){
  161.         //找到按下的关按钮对应的命令,并执行命令
  162.         offCommands[no].execute();
  163.         //记录这次操作,用于撤销
  164.         undoCommand = offCommands[no];
  165.     }
  166.     public void undoButtonWasPushed(){
  167.         undoCommand.undo();
  168.     }
  169. }
  170. public class Client {
  171.     public static void main(String[] args) {
  172.         RemoterController remoterController = new RemoterController();
  173.         //创建电灯接收者
  174.         LightReceiver lightReceiver = new LightReceiver();
  175.         //创建电灯的开指令
  176.         LightOffCommand lightOffCommand = new LightOffCommand(lightReceiver);
  177.         //创建电灯的关指令
  178.         LightOnCommand lightOnCommand = new LightOnCommand(lightReceiver);
  179.         //将电灯的开关指令,设置到遥控器中
  180.         remoterController.setCommand(0,lightOnCommand,lightOffCommand);
  181.         System.out.println("按下电灯的开按钮");
  182.         remoterController.onButtonWasPushed(0);
  183.         System.out.println("按下电灯的关按钮");
  184.         remoterController.offButtonWasPushed(0);
  185.         System.out.println("按下遥控器的撤销按钮");
  186.         remoterController.undoButtonWasPushed();
  187.         //创建电视接收者
  188.         TVReceiver tvReceiver = new TVReceiver();
  189.         //创建电视打开指令
  190.         TVOnCommand tvOnCommand = new TVOnCommand(tvReceiver);
  191.         //创建电视关闭指令
  192.         TVOffCommand tvOffCommand = new TVOffCommand(tvReceiver);
  193.         //将电视的开关指令,设置到遥控器中
  194.         remoterController.setCommand(1,tvOnCommand,tvOffCommand);
  195.         System.out.println("按下电视的开按钮");
  196.         remoterController.onButtonWasPushed(1);
  197.         System.out.println("按下电视的关按钮");
  198.         remoterController.offButtonWasPushed(1);
  199.         System.out.println("按下遥控器的撤销按钮");
  200.         remoterController.undoButtonWasPushed();
  201.     }
  202. }
复制代码
命令模式在Spring框架JdbcTemplate的源码分析

1.SpringTemplate类中使用到了命令模式
2.代码分析

3.角色分析
3.1 StatementCallback接口,类似命令接口Command.
3.2 class QueryStatementCallback implements StatementCallback, SqlProvider,局部内部类,在JdbcTemplate类的public  T query(final String sql, final ResultSetExtractor rse) 方法中,实现了命令接口,是指令的具体实现类,同时也是命令执行者角色。
3.3 命令调用者JdbcTemplate,其中execute(StatementCallback action),调用了action.doInStatement方法,不同的实现StatementCallback接口的对象,对应不同的
doInStatement实现逻辑
3.4 另外实现StatementCallbakc接口的类还有,如下图

注意事项和细节


免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!




欢迎光临 ToB企服应用市场:ToB评测及商务社交产业平台 (https://dis.qidao123.com/) Powered by Discuz! X3.4