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

Java 設計模式:模板方法模式 定義演算法骨架延遲步驟到子類

     編輯:Java 程式設計入門

模式定義

在抽象類中定義演算法骨架 (模板方法),將某些步驟延遲到子類實現。子類可在不改變演算法結構情況下,重新定義特定步驟。

角色結構

  • AbstractClass:定義模板方法 (final)、抽象步驟、鉤子方法 (可選)。
  • ConcreteClass:實現抽象步驟,可選覆寫鉤子方法。

經典案例:排序演算法框架

abstract class AbstractSort {
    // 模板方法:final 防止子類破壞流程
    public final void showSortResult(int[] arr) {
        sort(arr);                 // 抽象步驟:由子類實現
        printResult(arr);          // 具體步驟:統一列印
    }

    protected abstract void sort(int[] arr); // 必須實現

    // 鉤子方法:預設實現,子類可選覆寫
    protected boolean isAscending() { return true; }

    private void printResult(int[] arr) {
        System.out.print("排序結果: ");
        for (int v : arr) System.out.printf("%3d", v);
        System.out.println();
    }
}

// 子類:選擇排序
class SelectionSort extends AbstractSort {
    protected void sort(int[] arr) {
        for (int i = 0; i < arr.length - 1; i++) {
            int idx = i;
            for (int j = i + 1; j < arr.length; j++)
                if (arr[j] < arr[idx]) idx = j;
            int tmp = arr[i]; arr[i] = arr[idx]; arr[idx] = tmp;
        }
    }
}

// 子類:降序排序 (覆寫鉤子方法)
class DescendingSort extends SelectionSort {
    protected boolean isAscending() { return false; }
    // 若需改變列印邏輯,可覆寫 printResult (但它是 private,需改 protected)
}

// 客戶端
public class TemplateMethodDemo {
    public static void main(String[] args) {
        int[] data = {10, 32, 1, 9, 5, 7, 12, 0, 4, 3};
        new SelectionSort().showSortResult(data);  // 升序
        new DescendingSort().showSortResult(data); // 降序 (需配合打印邏輯)
    }
}

三種方法類型對比

類型定義者子類可否覆寫用途
抽象方法抽象類必須實現核心變化點
模板方法抽象類不可 (final)固定演算法流程
鉤子方法抽象類可選條件分支、預設行為、擴展點

優缺點與適用場景

  • 優點:復用不變邏輯、封裝變化點、符合開閉原則、便於維護 (單點修改流程)。
  • 缺點:每個變化點需一個子類 → 類爆炸;反向控制結構增加閱讀難度。
  • 適用:多子類共享相同演算法骨架、框架開發 (如 `HttpServlet.service()` → `doGet/doPost`)、資料庫遷移/ETL 固定流程。

JDK 內建範例

  • java.io.InputStream.read(byte[]) 模板方法呼叫抽象 read()。
  • java.util.AbstractList.addAll(int, Collection) 模板方法呼叫抽象 add(int, E)。
  • javax.servlet.http.HttpServlet.service() 分發到 doGet/doPost 等抽象方法。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved