デザインパターン学習メモ:「Command」
このパターンの目的
GoF本より引用する。
要求をオブジェクトとしてカプセル化することによって、異なる要求や、要求からなるキューやログにより、クライアントをパラメータ化する。また、取り消し可能なオペレーションをサポートする。
execute()のみをもつインタフェース(Java言語)を作成し、このインタフェースを実装したコマンド(命令)クラスを作る。
このコマンドクラスを要求として渡された処理の実行者は、その中身を知らなくてもexecute()を呼ぶことで実行することができる。つまり、処理の内部実装のカプセル化である。
さらに、カプセル化を用いて処理を抽象的に扱うことによって、共通の方法で要求の取り消しや再実行可能にする。
この場合は、状態の保存が必要になる。
実装例
『アジャイルソフトウェア開発の奥義』(P.203)をベースに作成。Commandパターンを利用したActive Objectパターンとして紹介されている。
// Command役
public interface Command {
public void execute();
}
// Invoker役
public class ActiveObjectEngine {
LinkedList<Command> itsCommands = new LinkedList<Command>();
public void addCommand(Command c) {
itsCommands.add(c);
}
// リストからコマンドを取り出し、一つずつ実行する
public void run() {
while(!itsCommands.isEmpty()) {
Command c = itsCommands.getFirst();
itsCommands.removeFirst();
c.execute();
}
}
}
// ConcreteCommand役
public class SimpleCommand implements Command {
private String name;
public SimpleCommand(String name) {
this.name = name;
}
@Override
public void execute() {
System.out.println("Executed by " + name);
}
}
// ConcreteCommand役
// 自身の処理が完了した後に、wakeUpCommandをEngineに登録する。
public class SleepCommand implements Command {
private String name;
private Command wakeUpCommand;
private ActiveObjectEngine engine;
private long sleepTimeMilliSec;
private long startTime;
private boolean started = false;
public SleepCommand(String name, long sleepTimeMilliSec,
ActiveObjectEngine engine, Command wakeUpCommand) {
this.name = name;
this.sleepTimeMilliSec = sleepTimeMilliSec;
this.engine = engine;
this.wakeUpCommand = wakeUpCommand;
}
@Override
public void execute() {
long currentTime = System.currentTimeMillis();
if (!started) {
System.out.println(name + " started.");
started = true;
startTime = currentTime;
engine.addCommand(this);
} else if ((currentTime - startTime) < sleepTimeMilliSec) {
engine.addCommand(this);
} else {
System.out.println("Executed by " + name);
engine.addCommand(wakeUpCommand);
}
}
}
実行例
public class Main {
public static void main(String[] args) {
ActiveObjectEngine engine = new ActiveObjectEngine();
engine.addCommand(new SimpleCommand("SimpleCommand-A"));
engine.addCommand(new SimpleCommand("SimpleCommand-B"));
engine.addCommand(new SleepCommand("SleepCommand-C", 3 * 1000, engine,
new SimpleCommand("WakeupCommand-C")));
engine.addCommand(new SimpleCommand("SimpleCommand-D"));
engine.run();
}
}
Executed by SimpleCommand-A
Executed by SimpleCommand-B
SleepCommand-C started.
Executed by SimpleCommand-D
Executed by SleepCommand-C
Executed by WakeupCommand-C
基本的に順番通りに各Commandが実行されている。SleepCommandだけは、意図通りSleepしているため、完了が最後になっている。
参考文献
- エリック ガンマ、ラルフ ジョンソン、リチャード ヘルム、ジョン プリシディース(1999)『オブジェクト指向における再利用のためのデザインパターン 改訂版』本位田 真一、吉田 和樹 監訳、SBクリエイティブ
- ロバート・C・マーチン(2004)『アジャイルソフトウェア開発の奥義 第2版 オブジェクト指向開発の神髄と匠の技』瀬谷啓介訳、SBクリエイティブ
Author And Source
この問題について(デザインパターン学習メモ:「Command」), 我々は、より多くの情報をここで見つけました https://qiita.com/aki3061/items/3e85c13d6ae5fce28c8c著者帰属:元の著者の情報は、元のURLに含まれています。著作権は原作者に属する。
Content is automatically searched and collected through network algorithms . If there is a violation . Please contact us . We will adjust (correct author information ,or delete content ) as soon as possible .