今天我們一起來(lái)看行為型設計模式中的命令模式、何為命令模式呢?先談命令——我現在需要對某一條信息進(jìn)行刪除,我進(jìn)行點(diǎn)擊刪除按鈕。后臺執行刪除的命令、對信息進(jìn)行刪除。那么我們要講的命令模式又是什么呢?命令模式就是把一個(gè)操作或者行為抽象為一個(gè)對象。然后通過(guò)對命令的抽象化來(lái)使得發(fā)出命令的職責和執行命令的職責分隔開(kāi)。簡(jiǎn)單來(lái)說(shuō)命令模式就是解決命令的請求者和命令的執行者之間的耦合關(guān)系的。
在我們開(kāi)發(fā)軟件系統的時(shí)候,命令的請求者和命令的執行者是屬于緊耦合的狀態(tài)。但是對于某些特殊場(chǎng)合這么一種緊耦合的狀態(tài)就不合適了。例如對行為命令的”日志記錄、撤銷(xiāo)/恢復、命令的隊列”等操作就不太合適了。那么在這些情況下如何對這些命令進(jìn)行統一的管理呢?實(shí)現其松耦合呢?
將一個(gè)請求封裝成一個(gè)對象,從而使您可以用不同的請求對客戶(hù)進(jìn)行參數化。

我們看上面的案例圖可以看到命令模式是包含了以下五個(gè)部分的:
客戶(hù)角色:創(chuàng )建具體的命令對象并確定命令對象的接收者
命令請求者:命令模式中最重要的角色、持有命令對象、實(shí)現對命令的控制、要求命令對象執行請求
命令接收者:真正的命令的執行者、實(shí)現具體功能
命令角色:聲明所有的命令的一個(gè)抽象類(lèi)
具體命令角色:命令接口實(shí)現對象、持有命令接收者、調用接收者完成命令的執行
在我們日常軟件開(kāi)發(fā)過(guò)程中必定會(huì )涉及到信息的增刪改查、一般的信息進(jìn)行操作也就罷了。但是對于一些重要的信息進(jìn)行操作的時(shí)候我們是否就需要對其進(jìn)行控制了。比如對其操作的日志的記錄。對操作命令的撤銷(xiāo)恢復。這里我們看看如何使用命令模式來(lái)對命令進(jìn)行控制操作:
namespace Command_Pattern{class CommandPattern { }#region 命令接收者——具體操作 ===================/// <summary>/// 執行命令/// </summary>public class InfoReceiver {public void Delete() { Console.WriteLine("刪除了第一條信息!"); }public void Update() { Console.WriteLine("更新了第二天信息!"); } }#endregion#region 命令請求者——控制命令 ===================/// <summary>/// 控制命令調用請求/// </summary>public class InfoInvoke {/// <summary>/// 記錄上一個(gè)命令/// </summary>private Command lastCommand =null;/// <summary>/// 接收當前命令/// </summary>private Command _command = null;public InfoInvoke(Command command=null) {this._command = command; }public string ExecuteInvoke() {if (_command==null&& lastCommand==null) return ("無(wú)命令執行!");if (_command == null) { Console.WriteLine($"記錄此操作記錄{_command.GetType().Name}的撤銷(xiāo)操作!"); _command = lastCommand;return ("執行撤銷(xiāo)操作!"); } Console.WriteLine($"記錄此操作記錄{_command.GetType().Name}!"); _command.Execute();return ("執行成功!"); } }#endregion#region 命令角色——抽象命令 =====================/// <summary>/// 抽象命令 持有命令接收者,調用接收者執行命令/// </summary>public abstract class Command {protected InfoReceiver _infoReceiver;public Command(InfoReceiver infoReceiver) {this._infoReceiver = infoReceiver; }public abstract void Execute(); }#endregion#region 具體命令角色——調用接收者 ===============/// <summary>/// 實(shí)現抽象角色/// </summary>public class InfoCommandDelete : Command { public InfoCommandDelete(InfoReceiver infoReceiver) : base(infoReceiver) { }public override void Execute() { _infoReceiver.Delete(); } }#endregion#region 具體命令角色——調用接收者 ===============/// <summary>/// 實(shí)現抽象角色/// </summary>public class InfoCommandUpdate : Command {public InfoCommandUpdate(InfoReceiver infoReceiver) : base(infoReceiver) { }public override void Execute() { _infoReceiver.Update(); } }#endregion}namespace Command_Pattern{class Program {static void Main(string[] args) {///初始化命令接收者和命令請求者還有具體命令InfoReceiver infoReceiver = new InfoReceiver(); InfoCommandDelete infoCommandDelete = new InfoCommandDelete(infoReceiver); InfoInvoke infoInvoke = new InfoInvoke(infoCommandDelete);var result=infoInvoke.ExecuteInvoke(); Console.WriteLine(result); } }}在命令模式中重點(diǎn)就是實(shí)現將“行為請求者”和“行為實(shí)現者”之間進(jìn)行解耦。而在命令請求者角色中可以對具體命令角色做一定的控制、同時(shí)也可以保存其額外的狀態(tài)信息。
1、認為是命令的地方都可以使用命令模式
2、系統支持命令的撤銷(xiāo)/恢復、重新執行等操作的時(shí)候可以考慮使用命令模式
3、命令的發(fā)送者和命令執行者有不同的生命周期,不要求命令發(fā)送必須立馬執行
4、命令需要進(jìn)行管理控制時(shí)
1、降低了系統的耦合性
2、新的命令可以很容易添加到系統中
3、可以將命令組合在一起形成合成命令
4、可以設計實(shí)現撤銷(xiāo)、重新執行的操作
1、使用命令模式可能導致有過(guò)多的具體命令類(lèi)、這樣會(huì )使系統變得不切實(shí)際。
到這里我們就介紹完了命令模式??偟膩?lái)說(shuō)命令模式是將”行為請求者”和”行為實(shí)現者”進(jìn)行了解耦。解耦之后就方便對命令進(jìn)行控制管理(操作信息日志記錄、撤銷(xiāo)/恢復操作、重新操作、命令隊列等等)。同時(shí)對新的命令加入也方便了一些(方便對命令擴展)。
一個(gè)人如若不能使自己的人生輝煌,但也沒(méi)有理由使它黯淡;人生可以平凡,但不可以庸俗、墮落;人生不在乎掠取多少,而在于追求過(guò)程的完美與卓越!
聯(lián)系客服