天天看點

設計模式(三)七大原則之(迪米特法則,合成複用原則)

目錄

迪米特法則

基本介紹

應用執行個體

應用執行個體改進

迪米特法則注意事項和細節

合成複用原則(Composite Reuse Principle)

基本介紹

設計原則核心思想

迪米特法則

基本介紹

1) 一個對象應該對其他對象保持最少的了解

2) 類與類關系越密切,耦合度越大

3) 迪米特法則(Demeter Principle)又叫最少知道原則,即一個類對自己依賴的類知道的越少越好。也就是說,對于

被依賴的類不管多麼複雜,都盡量将邏輯封裝在類的内部。對外除了提供的 public 方法,不對外洩露任何資訊

4) 迪米特法則還有個更簡單的定義:隻與直接的朋友通信

5) 直接的朋友:每個對象都會與其他對象有耦合關系,隻要兩個對象之間有耦合關系,我們就說這兩個對象之間是朋友關系。耦合的方式很多,依賴,關聯,組合,聚合等。其中,我們稱出現成員變量,方法參數,方法傳回值中的類為直接的朋友,而出現在局部變量中的類不是直接的朋友。也就是說,陌生的類最好不要以局部變量的形式出現在類的内部。

應用執行個體

1) 有一個學校,下屬有各個學院和總部,現要求列印出學校總部員工 ID和學院員工的 id

2) 程式設計實作上面的功能, 看代碼示範

3) 代碼示範

import java.util.ArrayList;
import java.util.List;
//用戶端
public class Demeter1 {
public static void main(String[] args) {
//建立了一個 SchoolManager 對象
SchoolManager schoolManager = new SchoolManager();
//輸出學院的員工 id 和 學校總部的員工資訊
schoolManager.printAllEmployee(new CollegeManager());
}
}
//學校總部員工類
class Employee {
private String id;
public void setId(String id) {
this.id = id;
}
public String getId() {
return id;
}
}


//學院的員工類
class CollegeEmployee {
private String id;
public void setId(String id) {
this.id = id;
}
public String getId() {
return id;
}
}
//管理學院員工的管理類
class CollegeManager {
//傳回學院的所有員工
public List<CollegeEmployee> getAllEmployee() {
List<CollegeEmployee> list = new ArrayList<CollegeEmployee>();
for (int i = 0; i < 10; i++) { //這裡我們增加了 10個員工到 list
CollegeEmployee emp = new CollegeEmployee();
emp.setId("學院員工 id= " + i);
list.add(emp);
}
return list;
}
}
//學校管理類
//分析 SchoolManager 類的直接朋友類有哪些 Employee、CollegeManager
//CollegeEmployee 不是 直接朋友 而是一個陌生類,這樣違背了 迪米特法則
class SchoolManager {
//傳回學校總部的員工
public List<Employee> getAllEmployee() {
List<Employee> list = new ArrayList<Employee>();
for (int i = 0; i < 5; i++) { //這裡我們增加了 5個員工到 list
Employee emp = new Employee();
emp.setId("學校總部員工 id= " + i);
list.add(emp);
}
return list;
}
//該方法完成輸出學校總部和學院員工資訊(id)
void printAllEmployee(CollegeManager sub) {
//分析問題
//1. 這裡的 CollegeEmployee 不是 SchoolManager 的直接朋友
//2. CollegeEmployee 是以局部變量方式出現在 SchoolManager

//3. 違反了 迪米特法則
//擷取到學院員工
List<CollegeEmployee> list1 = sub.getAllEmployee();
System.out.println("------------學院員工------------");
for (CollegeEmployee e : list1) {
System.out.println(e.getId());
}
//擷取到學校總部員工
List<Employee> list2 = this.getAllEmployee();
System.out.println("------------學校總部員工------------");
for (Employee e : list2) {
System.out.println(e.getId());
}
}
}
           

應用執行個體改進

1) 前面設計的問題在于 SchoolManager中,CollegeEmployee類并不是 SchoolManager類的直接朋友 (分析)

2) 按照迪米特法則,應該避免類中出現這樣非直接朋友關系的耦合

3) 對代碼按照迪米特法則 進行改進. (看老師示範)

4) 代碼示範

import java.util.ArrayList;
import java.util.List;
//用戶端
public class Demeter1 {
public static void main(String[] args) {
System.out.println("~~~使用迪米特法則的改進~~~");
//建立了一個 SchoolManager 對象
SchoolManager schoolManager = new SchoolManager();
//輸出學院的員工 id 和 學校總部的員工資訊
schoolManager.printAllEmployee(new CollegeManager());
}
}
//學校總部員工類
class Employee {
private String id;
public void setId(String id) {
this.id = id;
}

public String getId() {
return id;
}
}
//學院的員工類
class CollegeEmployee {
private String id;
public void setId(String id) {
this.id = id;
}
public String getId() {
return id;
}
}
//管理學院員工的管理類
class CollegeManager {
//傳回學院的所有員工
public List<CollegeEmployee> getAllEmployee() {
List<CollegeEmployee> list = new ArrayList<CollegeEmployee>();

for (int i = 0; i < 10; i++) { //這裡我們增加了 10個員工到 list
CollegeEmployee emp = new CollegeEmployee();
emp.setId("學院員工 id= " + i);
list.add(emp);
}
return list;
}
//輸出學院員工的資訊
public void printEmployee() {
//擷取到學院員工
List<CollegeEmployee> list1 = getAllEmployee();
System.out.println("------------學院員工------------");
for (CollegeEmployee e : list1) {
System.out.println(e.getId());
}
}
}
//學校管理類
//分析 SchoolManager 類的直接朋友類有哪些 Employee、CollegeManager
//CollegeEmployee 不是 直接朋友 而是一個陌生類,這樣違背了 迪米特法則
class SchoolManager {
//傳回學校總部的員工
public List<Employee> getAllEmployee() {

List<Employee> list = new ArrayList<Employee>();
for (int i = 0; i < 5; i++) { //這裡我們增加了 5個員工到 list
Employee emp = new Employee();
emp.setId("學校總部員工 id= " + i);
list.add(emp);
}
return list;
}
//該方法完成輸出學校總部和學院員工資訊(id)
void printAllEmployee(CollegeManager sub) {
//分析問題
//1. 将輸出學院的員工方法,封裝到 CollegeManager
sub.printEmployee();
//擷取到學校總部員工
List<Employee> list2 = this.getAllEmployee();
System.out.println("------------學校總部員工------------");
for (Employee e : list2) {
System.out.println(e.getId());
}
}
}
           

迪米特法則注意事項和細節

1) 迪米特法則的核心是降低類之間的耦合

2) 但是注意:由于每個類都減少了不必要的依賴,是以迪米特法則隻是要求降低類間(對象間)耦合關系,并不是

要求完全沒有依賴關系

合成複用原則(Composite Reuse Principle)

基本介紹

原則是盡量使用合成/聚合的方式,而不是使用繼承

設計模式(三)七大原則之(迪米特法則,合成複用原則)

設計原則核心思想

1) 找出應用中可能需要變化之處,把它們獨立出來,不要和那些不需要變化的代碼混在一起。

2) 針對接口程式設計,而不是針對實作程式設計。

3) 為了互動對象之間的松耦合設計而努力

繼續閱讀