命令模式是最簡單和優雅的模式之一,命令模式中的命令(command)指的是一個執行某些特定事情的指令。bash
命令模式最多見的應用場景是:有時候須要向某些對象發送請求,可是並不知道請求的接收 者是誰,也不知道被請求的操做是什麼。此時但願用一種鬆耦合的方式來設計程序,使得請求發送者和請求接收者可以消除彼此之間的耦合關係。ui
例如: 對於拿訂餐來講,客人須要向廚師發送請求,可是徹底不知道這些廚師的名字和聯繫方式,也不 知道廚師炒菜的方式和步驟。客人只關心菜品能準時上就行。this
// 模擬拳皇的場景
const Ryu = {
attack: () => { console.log('攻擊 => ',); },
defense: () => { console.log('防護 => ',); },
jump: () => { console.log('跳躍 => ',); },
crouch: () => { console.log('蹲下 => ',); },
};
const commands = {
119: 'jump', // W
115: 'crouch', // S
97: 'defense', // A
100: 'attack', // D
};
// 建立命令
const makeCommand = (receiver, state) => receiver[state];
const commandStack = [];
document.onkeypress = function(e) {
const command = makeCommand(Ryu, commands[e.keyCode]);
if (command) {
command(); // 執行命令
commandStack.push(command);
}
}
// 回放
const replay = document.getElementById('replay');
replay.onclick = function(e) {
let command;
while (command = commandStack.shift()){
command();
};
}
複製代碼
宏命令是一組命令的集合,經過執行宏命令的方式,能夠一次執行一批命令。批量執行, 至關於一鍵操做。想象一下,家 裏有一個萬能遙控器,天天回家的時候,只要按一個特別的按鈕,它就會幫咱們關上房間門,順便打開電腦並登陸 QQ。spa
const commandSet = {
closeDoor: () => { console.log('關上房門 => ',); },
openPc: () => { console.log('打開電腦 => ',); },
openQQ: () => { console.log('打開qq1 => ',); },
};
class MacroCommand {
commandList = [];
add = (command) => this.commandList.push(command);
execute = () => this.commandList.forEach((item) => item());
replay = () => {
let command;
while(command = this.commandList.shift()) {
command();
}
};
print = () => console.log('this.commandList => ',this.commandList);
}
const mc = new MacroCommand();
const { closeDoor, openPc, openQQ } = commandSet;
mc.add(closeDoor);
mc.add(openPc);
mc.add(openQQ);
mc.print();
setTimeout(mc.execute, 2000);
setTimeout(mc.replay, 5000);
複製代碼
通常來講,命令模式都會在 command 對象中保存一個接收者來負責真正執行客戶的請求,這種狀況下命令對象是「傻瓜式」的,它只負責把客戶的請求轉交給接收者來執行,這種模式的好處是請求發起者和請求接收者之間儘量地獲得瞭解耦。命令模式還能夠完成撤銷、排隊等功能。設計