Java設計模式之行為型模式(命令模式)

一、核心定義與設計思想

命令模式通過對象化請求,將操作的具體實現細節封裝在命令對象中,使得調用者(Invoker)無需直接依賴接收者(Receiver),僅需通過命令對象間接調用。這種設計支持以下能力:

  1. 解耦請求發送者與執行者:調用者僅與命令接口交互,無需了解接收者的實現細節。
  2. 支持擴展性與靈活性:新增命令只需實現接口,符合開閉原則。
  3. 實現高級功能:如撤銷(Undo)、重做(Redo)、事務管理及日志記錄。

二、模式結構與角色

命令模式包含以下核心角色:

  1. Command(抽象命令接口)
    聲明執行操作的統一接口,通常包含execute()方法,部分場景擴展undo()方法以支持撤銷。
    public interface Command { void execute(); void undo(); // 可選
    }
    
  2. ConcreteCommand(具體命令類)
    實現命令接口,持有接收者的引用并調用其方法。例如:
    public class LightOnCommand implements Command {private Light receiver;public LightOnCommand(Light receiver) { this.receiver = receiver; }public void execute() { receiver.turnOn(); }
    }
    
  3. Receiver(接收者)
    實際執行操作的對象,例如電燈、文本編輯器等業務邏輯實現類。
  4. Invoker(調用者)
    觸發命令執行的入口,不關心命令具體實現。例如遙控器或按鈕:
    public class RemoteControl {private Command command;public void pressButton() { command.execute(); }
    }
    
  5. Client(客戶端)
    創建具體命令對象并綁定接收者,將其傳遞給調用者。

三、代碼示例與實現

場景:遙控器控制家電(經典案例)

  1. 定義接收者
    class Light {public void turnOn() { System.out.println("燈已開啟"); }public void turnOff() { System.out.println("燈已關閉"); }
    }
    
  2. 實現具體命令
    class LightOnCommand implements Command {private Light light;public LightOnCommand(Light light) { this.light = light; }public void execute() { light.turnOn(); }
    }
    
  3. 調用者與客戶端交互
    public class Client {public static void main(String[] args) {Light light = new Light();Command cmdOn = new LightOnCommand(light);RemoteControl control = new RemoteControl();control.setCommand(cmdOn);control.pressButton(); // 輸出:燈已開啟}
    }
    
    結果:調用者與接收者完全解耦,支持靈活替換命令。

四、高級應用場景

  1. 撤銷與重做(Undo/Redo)
    通過維護命令歷史棧實現操作回滾。例如文本編輯器的撤銷功能:
    class Editor {private String text;public void insert(String content) { /* 實現 */ }public void delete(String content) { /* 實現 */ }
    }
    class InsertCommand implements Command {private Editor receiver;private String content;public void execute() { receiver.insert(content); }public void undo() { receiver.delete(content); }
    }
    
  2. 宏命令(Macro Command)
    將多個命令組合為一個復合命令,實現批量操作:
    class MacroCommand implements Command {private List commands = new ArrayList<>();public void add(Command cmd) { commands.add(cmd); }public void execute() { commands.forEach(Command::execute); }
    }
    
  3. 異步任務隊列
    結合線程池處理異步請求,提升系統吞吐量:
    class CommandQueue {private BlockingQueue queue = new LinkedBlockingQueue<>();public void addCommand(Command cmd) { queue.put(cmd); }public void process() { queue.forEach(cmd -> new Thread(cmd::execute).start()); }
    }
    

五、優缺點分析

優點缺點
解耦請求發送者與接收者,提升系統靈活性可能導致類爆炸問題(每個操作需獨立命令類)
支持撤銷、重做及事務管理,增強用戶體驗增加系統復雜度,需額外維護命令對象
符合開閉原則,擴展性強過度設計風險,簡單場景可能不必要

六、適用場景

  1. GUI事件處理:如按鈕點擊、菜單操作。
  2. 事務性操作:數據庫事務的提交與回滾。
  3. 日志與審計:記錄操作歷史以便恢復。
  4. 異步任務調度:如消息隊列中的任務處理。

七、與其他模式的對比

  • 策略模式:關注算法替換,而命令模式關注請求封裝。
  • 觀察者模式:通過訂閱-發布解耦,命令模式通過對象化請求解耦。
  • 責任鏈模式:請求逐級傳遞,命令模式明確單一行執行路徑。

總結

命令模式通過對象化請求實現了高度解耦與靈活控制,是構建可擴展系統的利器。其核心價值在于將操作抽象為對象,支持復雜功能(如撤銷、異步隊列)的同時降低系統耦合度。實際應用中需根據場景權衡復雜性,避免濫用。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/88952.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/88952.shtml
英文地址,請注明出處:http://en.pswp.cn/web/88952.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

大數據領域開山鼻祖組件Hadoop核心架構設計

一、Hadoop的整體架構 Hadoop是一個專為大數據設計的架構解決方案&#xff0c;歷經多年開發演進&#xff0c;已逐漸發展成為一個龐大且復雜的系統。其內部工作機制融合了分布式理論與具體工程開發的精髓&#xff0c;構成了一個整體架構。 Hadoop最樸素的原理在于&#xff0c;它…

OneCode3.0 VFS分布式文件管理API速查手冊

&#x1f4da; 前言&#xff1a;OneCode 3.0微內核引擎架構解析 在云原生與分布式系統日益普及的今天&#xff0c;文件管理系統面臨著前所未有的挑戰——海量數據存儲、跨節點協同、多租戶隔離以及彈性擴展等需求推動著傳統文件系統向分布式架構演進。OneCode 3.0作為新一代企業…

UI前端與數字孿生結合實踐探索:智慧物流的倉儲自動化管理系統

hello寶子們...我們是艾斯視覺擅長ui設計、前端開發、數字孿生、大數據、三維建模、三維動畫10年經驗!希望我的分享能幫助到您!如需幫助可以評論關注私信我們一起探討!致敬感謝感恩!一、引言&#xff1a;傳統倉儲的 “效率黑洞” 與數字孿生的破局當倉庫管理員在數萬平的庫房中…

使用layui的前端框架過程中,無法加載css和js怎么辦?

這使用layui的前端框架過程中&#xff0c;無法加載css和js怎么辦&#xff1f;里寫自定義目錄標題已經按要求下載并解壓到指定位置了&#xff0c;但是感覺就是無法加載文件后臺提示如下&#xff1a;那就我清理緩存當再次觀察html頁面時&#xff0c;發現頁面最開始有兩個< htm…

gitlab+TortoiseGit克隆生成ppk方式

1、第一步 2、第二步3、第三步4、第四步&#xff0c;如何使用這個ppk就可以了

VSCode中使用容器及容器編排docker-compose

前面筆者寫了一篇博文&#xff1a;使用容器編排對go項目進行部署、調試&#xff0c;介紹了在Goland中如何使用容器&#xff0c;由于Goland的容器配置是可視化的&#xff0c;使用起來非常方便&#xff0c;VSCode中也有一個容器插件&#xff0c;但是筆者一直未使用過&#xff0c;…

深度學習入門:讓神經網絡變得“深不可測“?(二)

深度學習入門&#xff1a;讓神經網絡變得"深不可測" &#x1f9e0;? 系列課程第二彈&#xff1a;深度學習的奇妙世界 前言&#xff1a;從淺到深的華麗轉身 哈嘍&#xff0c;各位AI探險家&#xff01;&#x1f44b; 歡迎回到我們的"讓機器變聰明"系列課…

硅基計劃2.0 學習總結 捌 異常與常用工具類

文章目錄一、異常1. 防御性編程2. throw關鍵字3. throws關鍵字4. 捕獲5. finally關鍵字二、自定義異常類三、常用工具類1. Date以及相關的類1. 創建時間&#xff08;基本棄用&#xff09;2. 捕獲系統時間3. 獲取當前年月日時分秒4. 日期加減5. 根據字符串創建日期6. 根據當前時…

2025-7-14-C++ 學習 排序(2)

文章目錄2025-7-14-C 學習 排序&#xff08;2&#xff09;P1059 [NOIP 2006 普及組] 明明的隨機數題目描述輸入格式輸出格式輸入輸出樣例 #1輸入 #1輸出 #1說明/提示提交代碼P1093 [NOIP 2007 普及組] 獎學金題目背景題目描述輸入格式輸出格式輸入輸出樣例 #1輸入 #1輸出 #1輸入…

微信131~140

1.在組件中使用store對象的數據 // 要想使用store中的數據以及方法 // 需要從 mobx-miniprogram-bindings 方法將 ComponentWithStore 方法 import { ComponentWithStore } from mobx-miniprogram-bindings // 導入store對象 import { numStore } from ../../../stores/numstor…

微美全息借區塊鏈與DRL算法打造資源管理協同架構,達成邊緣計算與區塊鏈動態適配

在當今數字化浪潮洶涌的時代&#xff0c;邊緣計算與區塊鏈技術正逐步成為驅動技術革新與業務轉型升級的核心動力。當這兩項前沿技術相互融合&#xff0c;一個兼具高效性與安全性的任務處理系統便得以構建。為了充分挖掘邊緣計算系統的性能潛力&#xff0c;避免任務卸載過程中的…

屬性綁定

簡寫模式二.為什么要這樣做布爾型attribute動態綁定多個值

鏈表算法之【獲取鏈表開始入環的節點】

目錄 LeetCode-142題 LeetCode-142題 給定一個鏈表的頭節點head&#xff0c;返回鏈表開始入環的第一個節點&#xff0c;如果鏈表無環&#xff0c;則返回null class Solution {public ListNode detectCycle(ListNode head) {// checkif (head null || head.next null)retur…

【網絡編程】KCP——可靠的 UDP 傳輸協議——的知識匯總

文章目錄前言UDP 協議UDP 的關鍵指標/特性UDP 的典型應用場景KCP 協議的基礎KCP 的構造KCP 協議特性KCP 的可靠傳輸機制——ARQ三種 ARQ 機制對比KCP 的選擇性重傳一、基礎機制&#xff1a;選擇性重傳&#xff08;SR&#xff09;二、KCP 對 SR 的增強策略KCP 的激進重傳策略——…

量子計算新突破!阿里“太章3.0”實現512量子比特模擬(2025中國量子算力巔峰)

??摘要??2025年量子計算競爭進入??實用化臨界點??&#xff0c;阿里達摩院發布“太章3.0”量子模擬器&#xff0c;在全球首次實現??512量子比特全振幅模擬??&#xff0c;較谷歌Sycamore的53比特提升近10倍算力維度。本文深度解析三大技術突破&#xff1a;??張量網…

DOM事件綁定時機:解決腳本提前加載導致的綁定失敗

引言&#xff1a;一個讓無數新手抓狂的常見錯誤在JavaScript開發中&#xff0c;尤其是在前端領域&#xff0c;有一個讓無數新手抓狂的問題&#xff1a;明明寫了事件監聽代碼&#xff0c;點擊按鈕卻沒有任何反應&#xff01;更令人困惑的是&#xff0c;代碼邏輯看起來完全正確&a…

游戲框架筆記

游戲的數據有哪些類型無非是只讀數據&#xff08;各種道具配表里的數據&#xff09;和可讀可寫數據&#xff08;玩家屬性、擁有的物品&#xff09;。游戲框架需要哪些管理器用戶數據管理器負責找到數據持久化文件&#xff0c;從中讀取指定用戶的數據&#xff0c;包括玩家的設置…

【C語言進階】指針面試題詳解(2)

上一期內容&#xff0c;大多數的解題思路寫在代碼中&#xff0c;沒有寫在正文中&#xff0c;這就導致系統判斷文章質量不高&#xff0c;沒有什么數據&#xff0c;這一期將思路寫在正文中。注意&#xff1a;運行環境是x86 1.題目1思路&#xff1a;&a是取到了整個數組的地址&…

一文讀懂現代卷積神經網絡—稠密連接網絡(DenseNet)

目錄 什么是 DenseNet&#xff1f; 稠密塊&#xff08;Dense Block&#xff09;詳解 一、稠密塊的核心思想 二、稠密塊的結構組成 1. 卷積單元&#xff08;的結構&#xff09; 2. 密集連接的具體方式 3. 關鍵參數&#xff1a;增長率&#xff08;Growth Rate, k&#xff0…

關于僵尸進程

深入理解僵尸進程&#xff1a;成因、危害與解決方案 進程終止的條件 我們先了解一下進程銷毀的條件&#xff1a; 調用了exit函數在main函數中執行了return語句 無論采用哪種方式&#xff0c;都會有一個返回值&#xff0c;這個返回值由操作系統傳遞給該進程的父進程。操作系統不…