摘要:什么是組合模式什么是組合模式組合模式將對象組合成樹形結構以表示部分整體的層次結構,使得用戶對單個對象和組合對象的使用具有一致性。組合模式應用場景組合模式應用場景只要是樹形結構,就可以考慮使用組合模式。
Compose objects into tree structures to represent part-whole hierarchies.Composite lets clients treat individual objects and compositions of objects uniformly.
組合模式(Composite Pattern):將對象組合成樹形結構以表示“部分-整體”的層次結構, 使得用戶對單個對象和組合對象的使用具有一致性。
說人話:用于處理樹形結構數據。
①、Component 抽象構件角色
定義參加組合對象的共有方法和屬性,可以定義一些默認的行為或屬性。
②、Leaf 葉子節點
葉子對象,其下再也沒有其他的子節點,是遍歷的最小單位。
③、Composite 樹枝構件
樹枝對象,作用是組合樹枝節點和葉子節點形成一個樹形結構。
/** * 個體和整體的抽象 */public abstract class Component { // 個體和整體都有的共享 public void doSomething(){ // 通用業務邏輯 System.out.println("通用業務邏輯"); }}
/** * 樹枝節點 */public class Composite extends Component{ // 構件容器 private ArrayList componentArrayList = new ArrayList<>(); // 增加一個葉子節點或者樹枝節點 public void add(Component component){ this.componentArrayList.add(component); } // 刪除一個葉子節點或者樹枝節點 public void remove(Component component){ this.componentArrayList.remove(component); } // 獲取分支下所有葉子節點和樹枝節點 public List getChildren(){ return this.componentArrayList; }}
/** * 葉子節點 */public class Leaf extends Component { // 覆寫父類方法 @Override public void doSomething() { // 葉子節點邏輯 System.out.println("葉子節點邏輯"); }}
測試:
public class ClientTest { public static void main(String[] args) { // 創建一個根節點 Composite root = new Composite(); root.doSomething(); // 創建一個樹枝構件 Composite branch = new Composite(); // 創建一個葉子節點 Leaf leaf = new Leaf(); // 串聯起來 root.add(branch); branch.add(leaf); display(root); } // 通過遞歸遍歷數 public static void display(Composite root){ for(Component c : root.getChildren()){ if(c instanceof Leaf){ // 葉子節點 c.doSomething(); }else{ display((Composite) c); } } }}
這里我們在舉一個例子:
假設我們在開發一個 OA 系統(辦公自動化系統)。公司的組織結構包含部門和員工兩種數據類型。其中,部門又可以包含子部門和員工。
我們希望在內存中構建整個公司的人員架構圖(部門、子部門、員工的隸屬關系),并且提供接口計算出部門的薪資成本(隸屬于這個部門的所有員工的薪資和)。
/** * 部門類和員工類的抽象類 */public abstract class HumanResource { protected long id; protected double salary; public HumanResource(long id){ this.id = id; } public long getId(){ return id; } public abstract double calculateSalary();}
public class Department extends HumanResource{ private List subNodes = new ArrayList<>(); public Department(long id){ super(id); } @Override public double calculateSalary() { double totalSalary = 0d; for (HumanResource hr : subNodes){ totalSalary += hr.calculateSalary(); } this.salary = totalSalary; return totalSalary; } public void addSubNode(HumanResource humanResource){ subNodes.add(humanResource); }}
public class Employee extends HumanResource{ public Employee(long id,double salary){ super(id); this.salary = salary; } @Override public double calculateSalary() { return salary; }}
測試:
public class PersonClientTest { private static final long ORGANIZATION_ROOT_ID = 1; public static void main(String[] args) { // 創建總部門 Department root = new Department(ORGANIZATION_ROOT_ID); // 創建子部門 Department branch = new Department(2L); // 創建員工 Employee employee1 = new Employee(21L,2000); Employee employee2 = new Employee(22L,4000); root.addSubNode(branch); branch.addSubNode(employee1); branch.addSubNode(employee2); double v = root.calculateSalary(); System.out.println(v); } private void buildOrganization(Department department){ // 根據 部門id 查詢數據庫 所有下屬部門 id // List subDepartmentIds = departmentRepo.getSubDepartmentIds(department.getId()); List subDepartmentIds = new ArrayList<>(); for (Long subDepartmentId : subDepartmentIds){ Department subDepartment = new Department(subDepartmentId); department.addSubNode(subDepartment); buildOrganization(subDepartment); } // 根據部門id 查詢數據庫 其關聯員工所有 id // List employeeIds = employeeRepo.getDepartmentEmployeeIds(department.getId()); List employeeIds = new ArrayList<>(); for (Long employeeId : employeeIds){ // 根據 employeeId 查詢數據庫得到 salary // 假設為 1000 double salary = 1000d; department.addSubNode(new Employee(employeeId,salary)); } }}
①、高層模塊調用簡單
一棵樹形機構中的所有節點都是Component, 局部和整體對調用者來說沒有任何區別,也就是說, 高層模塊不必關心自己處理的是單個對象還是整個組合結構, 簡化了高層模塊的代碼。
②、節點自由增加
使用了組合模式后, 如果想增加一個樹枝節點、 葉子節點都很容易, 只要找到它的父節點就成, 非常容易擴展, 符合開閉原則, 對以后的維護非常有利。
只要是樹形結構,就可以考慮使用組合模式。
①、維護和展示部分-整體關系的場景, 如樹形菜單、 文件和文件夾管理。
②、從一個整體中能夠獨立出部分模塊或功能的場景
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/125676.html
摘要:我們今天也來做一個萬能遙控器設計模式適配器模式將一個類的接口轉換成客戶希望的另外一個接口。今天要介紹的仍然是創建型設計模式的一種建造者模式。設計模式的理論知識固然重要,但 計算機程序的思維邏輯 (54) - 剖析 Collections - 設計模式 上節我們提到,類 Collections 中大概有兩類功能,第一類是對容器接口對象進行操作,第二類是返回一個容器接口對象,上節我們介紹了...
摘要:哪吒社區技能樹打卡打卡貼函數式接口簡介領域優質創作者哪吒公眾號作者架構師奮斗者掃描主頁左側二維碼,加入群聊,一起學習一起進步歡迎點贊收藏留言前情提要無意間聽到領導們的談話,現在公司的現狀是碼農太多,但能獨立帶隊的人太少,簡而言之,不缺干 ? 哪吒社區Java技能樹打卡?【打卡貼 day2...
摘要:方法即為收集器,它接收高階函數和的后端掘金年的第一天,我坐在獨墅湖邊,寫下這篇文章。正因如此,所以最全系列教程后端掘金是從版本開始引入的一個新的,可以替代標準的。 設計模式之單例模式 - 掘金前言 作為一個好學習的程序開發者,應該會去學習優秀的開源框架,當然學習的過程中不免會去閱讀源碼,這也是一個優秀程序員的必備素養,在學習的過程中很多人會遇到的障礙,那就是設計模式。很多優秀的框架會運...
閱讀 3788·2023-01-11 11:02
閱讀 4294·2023-01-11 11:02
閱讀 3113·2023-01-11 11:02
閱讀 5229·2023-01-11 11:02
閱讀 4788·2023-01-11 11:02
閱讀 5564·2023-01-11 11:02
閱讀 5366·2023-01-11 11:02
閱讀 4063·2023-01-11 11:02