首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 相關知識

責任鏈模式在 Java 中的實戰應用:從原理到代碼生成器重構

     編輯:Java 相關知識

模式本質:解耦請求發送者與接收者

責任鏈模式將多個處理者對象鏈接成鏈,請求沿鏈傳遞,直到某處理者處理為止。核心價值:

  • 發送者無需知道誰處理請求(解耦)
  • 動態組合/調整處理邏輯(靈活)
  • 單一職責:每個處理者只關注特定邏輯

角色結構

角色職責代碼體現
Handler(抽象處理者)定義處理接口、持有後繼者引用interface / abstract class
ConcreteHandler(具體處理者)實現具體邏輯,決定:處理 / 轉發 / 兩者兼有實現類
Client(客戶端)組裝鏈、發起請求構建鏈、調用 head.handle()

純與不純:別被教條束縛

  • 純責任鏈:處理者非處理即轉發,請求必被某節點處理
  • 不純責任鏈:允許部分處理後轉發、請求可能無人處理
  • 實戰原則:「管它黑貓白貓,抓住老鼠就是好貓」 —— 滿足低耦合、高內聚、易擴展即可

實戰案例:代號自動生成器重構

業務背景

系統需生成員工工號、檔案代號等,規則包含年份、月份、日期、流水號等可變元素,且未來可能擴展新元素。

重構前:巨大的 if-else / switch

// 違反開閉原則,新增元素需修改核心邏輯
public String[] generateCode(String rule) {
    if (rule.contains("YYYY")) { /* 年份邏輯 */ }
    if (rule.contains("MM")) { /* 月份邏輯 */ }
    // ... 越來越長、難維護
}

重構後:責任鏈 + Spring 管理

// 1. 統一處理接口
public interface CodeAutoParse {
    String[] generateCode(String moduleCode, int number, String rule, String[] target) throws BaseException;
}

// 2. 日期處理器
@Component
public class DateAutoParse implements CodeAutoParse {
    private final Calendar currentDate = Calendar.getInstance();
    @Autowired(required = false)  // 可選後繼者
    private CodeAutoParse nextParse;

    public String[] generateCode(String moduleCode, int number, String rule, String[] target) throws BaseException {
        // 解析規則中的日期佔位符(YYYY, MM, DD 等)
        // ... 業務邏輯省略
        return (nextParse != null) ? nextParse.generateCode(moduleCode, number, rule, target) : target;
    }
}

// 3. 流水號處理器
@Component
public class SequenceAutoParse implements CodeAutoParse {
    @Autowired(required = false)
    private CodeAutoParse nextParse;
    // ... 類似結構
}

// 4. Spring 配置鏈順序(applicationContext.xml 或 @Order)
/*
<bean id="dateParse" class="com.example.DateAutoParse">
    <property name="nextParse" ref="sequenceParse"/>
</bean>
<bean id="sequenceParse" class="com.example.SequenceAutoParse">
    <property name="nextParse" ref="customParse"/>
</bean>
*/

新增元素只需:

  1. 實現 CodeAutoParse 接口
  2. 在 Spring 配置中插入鏈路適當位置
  3. 零修改現有處理器代碼

經典場景:Java AWT 1.0 事件浮升(不純責任鏈)

public boolean action(Event event, Object obj) {
    if (event.target == btnOK) { doOKBtnAction(); }
    else if (event.target == btnExit) { doExitBtnAction(); }
    else { return super.action(event, obj); }  // 向父容器傳播
    return true;  // true = 停止傳播,false = 繼續傳播
}
  • 每個組件可選擇處理、或傳播、或兩者兼有
  • 事件可在任意層級被攔截停止
  • 典型不純責任鏈

優缺點總結

優點缺點
降低耦合:發送者/接收者互不知曉 性能開銷:請求需遍歷鏈(可通過鏈長度控制、優先級優化)
動態靈活:運行時增刪/調序處理者 調試困難:調用鏈隱式,日誌需記錄鏈路信息
單一職責:每類邏輯獨立封裝 遞歸深度:極長鏈可能導致 StackOverflow

與其他模式協作

  • 組合模式:處理者鏈常為樹結構一部分(如 AWT 組件樹)
  • 命令模式:請求對象化(Command Object),解耦請求參數與處理邏輯
  • 模板方法:抽象處理者定義骨架,子類實現具體步驟

總結

責任鏈模式不是「鏈表數據結構」的同義詞,而是「職責分發」的架構思想。在 Java 中配合 Spring 依賴注入管理鏈路組裝,能將業務規則變更點隔離在單獨 Handler 中,實現「對擴展開放,對修改關閉」。無論純與不純,關鍵在於:識別系統中「可變的處理邏輯」,將其封裝為獨立 Handler,通過配置而非代碼修改來組合行為。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved