熱點推薦:
您现在的位置: 電腦知識網 >> 編程 >> Java編程 >> Java核心技術 >> 正文

項目重構之命令模式

2013-11-23 19:32:36  來源: Java核心技術 

  項目中有個業務處理類大小K代碼看此類差點雷死我如今如要增加業務邏輯大約個吧此類如果隨著項目工程的二期三期如次添加邏輯遲早有一天大小達到Mmygod細心研讀前人的工作總結發現其中有點可改造的蛛絲馬跡(本人很笨別笑我才發現如何改造)

  下面我們對業務流程以及涉及的相關類進行介紹Msg代表接受到客戶端的一個消息報文消息報文結構消息頭+消息體消息頭參數固定消息體參數不定下面是一個簡單的類圖這只是一個模擬場景****Req代表各戶端請求類***Rsp代表返回給客戶端的參數類實際比此復雜為描述問題我們簡單摘除幾個類介紹別問我為何這麼設計繼承類圖msg與msgHead是組合關系也許畫錯了不當之處請指出勿惡語向傷

  處理請求Handler類的代碼邏輯如下

  Java代碼

  //類中主要方法如下

  public void execute(Object object) {

  Message message = (Message)object;

  int opcode = messagegetOpcode();

  int connectId = messagegetConnectId();

  //消息頭已經解析獲取消息體即子類屬性字節數組

  byte[] bytes = messagegetBytes();

  if (opcode == MsgInfoADD_RING) {

  // 訂購彩鈴

  orderRing(connectId bytes);

  } else if (opcode == MsgInfoPRESENT_RING) {

  // 贈送彩鈴

  presentRing(connectId bytes);

  } else if (opcode == MsgInfoDEL_RING) {

  // 刪除個人鈴音

  delPersonalRing(connectId bytes);

  }

  //此處省略n個else if

  }

  //其他刪除贈送與省略的else if中的處理邏輯與之基本相同

  private void orderRing(int connectId byte[] bytes) {

  //處理方法分為四步具體代碼省略

  //解析字節數組為訂購鈴音類

  //處理訂購關系

  //處理結果封裝為訂購響應類

  //發送回客戶端

  }

  //省略presentRingdelPersonalRing等一系列其他方法所有的處理方法參數相同……

  鑒於此想到使用命令模式改造此類如果不了解命令模式請閱讀相關書籍大話設計模式或設計與模式這裡我們僅給出大致的定於與類圖

  何謂命令模式將一個請求封裝為一個對象從而是你可用不同的請求對客戶端參數化對請求排隊或記錄日志以及支持可撤銷的操作

  Shit這句話很難理解哦那就先別理解了我們看下命令模式的類圖然後介紹如何使用命令模式改造上面的elseif

  類圖先省略上班偷空寫的

  下面進入正題對Handler小手術開始主要考慮如下

  提煉方法

  將每個if語句塊中的邏輯提取為一個方法這裡我們的handler已經實現就是orderRingpresentRingdelPersonalRing……

  提煉類

  將每個業務處理方法提取為以各類然後對具體類進行抽象提取父類或者接口代碼如下

  Java代碼

  public Abstract class Command{

  public void execute()

  }

  public class OrderRingCommand extends Command {

  private Handler hander;

  public OrderRingCommand(Handler hander){

  thishander = hander;

  }

  public void execute(int connectId byte[] bytes){

  //解析字節數組為訂購鈴音類

  //增加訂購關系

  //處理結果封裝為訂購響應類

  //發送回客戶端

  }

  /**

  * 解析字節數組為訂購鈴音類

  */

  public void method(){

  }

  /**

  * 處理訂購關系

  */

  public void method(){

  }

  /**

  * 處理結果封裝為訂購響應類

  */

  public void method(){

  }

  /**

  * 結果發送回客戶端

  */

  public void method(){

  }

  }

  public class DelRingCommand extends Command {

  private Handler hander;

  public DelRingCommand(Handler hander){

  thishander = hander;

  }

  public void execute(int connectId byte[] bytes){

  //解析字節數組為訂購鈴音類

  //刪除購關系

  //處理結果封裝為訂購響應類

  //發送回客戶端

  }

  //提取方法

  }

  命令模式改造替換elseif

  Java代碼

  Map<Integer Command> map = new HashMap<IntegerCommand>();

  static{

  mapput(MsgInfoADD_RING new OrderRingCommand());

  //省卻其他這裡僅為演示實際項目中實例化類通過spring容器或者其他方法

  }

  public void execute(Object object) {

  Message message = (Message)object;

  int opcode = messagegetOpcode();

  int connectId = messagegetConnectId();

  //消息頭已經解析獲取消息體即子類屬性字節數組

  byte[] bytes = messagegetBytes();

  mapget(opcode)execute(connectIdbytes);

  }

  命令模式替換else if代碼壞味道的重構結束眾多的if條件塊煙消雲散取而代之的是一個個精簡的類


From:http://tw.wingwit.com/Article/program/Java/hx/201311/27066.html
    推薦文章
    Copyright © 2005-2013 電腦知識網 Computer Knowledge   All rights reserved.