設計原則:ø
「開-閉」原則,
open-closed principle
(ocp) ø
黎克特制代替原則,
liskov subsitution principle
(lsp) ø
依賴倒轉原則,
dependency inversion principle
(dip) ø
介面隔離原則,
inte***ce segregation principle
(isp) ø
組合/聚合復用原則,
composition/aggregation principle
(carp) ø
迪公尺特法則,
law of demeter
(lod)
「開-
閉」原則:
software entities should be open for extension,bu closed for modification
。在設計乙個模組的時候,應該使這個模組可以在不被修改的前提下被擴充套件。
另外乙個角度講述:對可變性的封裝原則,
principle of encapsulation of variation
,evp
。對可變性的封裝原則是指:找到乙個系統的可變因素,將之封裝起來。
「對可變性的封裝原則」意味著兩點:
1、一種可變性不應當散落在**的很多角落,而應當被封裝到乙個物件裡面。延伸含義:繼承應當被看做是封裝變化的方法,而不應當被認為是從一般的物件生成特殊的物件的方法。
2、一種可變性不應當與另一種可變性混合在一起。延伸含義:類的繼承結構不應該超過兩層,不然就意味著將兩種不同的可變性混合在了一起。
黎克特制代換原則:
如果對每乙個型別為
t1的物件
o1,都有型別為
t2的物件
o2,使得以
t1定義的所有程式
p在所有的物件
o1都代換為
o2時,程式
p的行為沒有變化,那麼型別
t2是型別
t1的子型別。換言之,乙個軟體實體如果使用的是乙個基類的話,那麼一定適用於其子類,而且它根本不能察覺出基類物件和子類物件的區別。
依賴倒轉原則:
abstractions should not depend upon details.details should depend upon abstractions.
抽象不應當依賴於細節;細節應當依賴於抽象。
另一種表述:
program to an inte***ce, not an implementation.
要針對介面程式設計,不要針對實現程式設計。
依賴倒轉原則優缺點:
1、
物件的建立很有可能使用物件工廠,已避免對具體類的直接引用,此原則的使用還會導致大量地類。
2、依賴倒轉原則假定所有的具體類都是會變化的,這也不總是正確的。有一些具體類可能是相當穩定、不會發生變化的,消費這個具體類例項的客戶端完全可以依賴於這個具體型別,而不必為此發明乙個抽象型別。
介面隔離原則:
使用多個專門的介面比使用單一的總介面要好。
另一種表述:乙個類對另外乙個類的依賴性應該是建立在最小的介面上的。
過於臃腫的介面是對介面的汙染(
inte***ce contamination
)。準確而恰當地劃分角色以及角色所對應的介面,是物件導向的設計的乙個重要的組成部分。
合成/
聚合復用原則:
經常又叫做:合成復用原則,
composite reuse principle
,crp
在乙個新的物件裡面使用一些已有的物件,是指成為新的物件的一部分;新的物件通過向這些物件委派達到復用已有功能的目的。
另乙個表述:要盡量使用合成
/聚合,盡量不要使用繼承。
合成(composition
)和聚合(
aggregation
)均是關聯(
association
)的特殊種類。聚合用來表示「擁有」關係或者整體與部分的關係;而合成則用來表示一種強得多的「擁有」關係。在乙個合成關係裡,部分和整體的生命週期是一樣。乙個合成的新的物件完全擁有對其組成部分的支配權,包括它們的建立和湮滅等。使用程式語言的術語來講,組合而成的新物件對組成部分的記憶體分配、記憶體釋放有絕對的責任。
乙個合成的多重性(
multiplicity
)不能超過
1,換言之,乙個合成關係中的成分物件是不能與另乙個合成關係共享的。
合成
/聚合復用的優點:1、
新物件訪問成分物件的唯一方法是通過成分物件的介面。
2、這種復用是黑箱復用,因為成分物件的內部細節是新物件所看不見的。
3、這種復用支援包裝。
4、這種復用所需的依賴較少。
5、每乙個新的類可以可以將焦點集中在乙個任務上。
6、這種復用可以在執行時間內動態進行,新物件可以動態地引用與成分物件型別相同的物件。
合成
/聚合復用的缺點:通過使用這種復用建造的系統會有較多的物件需要管理。
繼承復用的優點:
1、
新的實現較為容易,因為超類的大部分功能可以通過繼承關係自動進入子類。
2、修改或擴充套件繼承而來的實現較為容易。
繼承復用的缺點:
1、
繼承復用破壞包裝,因為繼承將超類的實現細節暴露給子類。由於超類的內部細節常常是對子類透明的,因此這種復用是透明的復用,又稱「白箱」復用。
2、如果超類的實現發生改變,那麼子類的實現也不得不發生改變。因此,當乙個基類發生改變時,這種改變會像水中投入石子引起的水波一樣,將變化一圈又一圈地傳導到一級又一級的子類,使設計師不得不相應地改變這些子類,以適應超類的變化。
3、從超類繼承而來的實現是靜態的,不可能在執行時間內發生改變,因此沒有足夠的靈活性。
只要有可能,不要從具體類繼承。
抽象類應當擁有盡可能多的共同**,應當擁有盡可能少的資料。
只有當以下條件都被滿足時,才應當使用繼承關係:
1、
子類是超類的乙個特殊種類,而不是超類的乙個角色,也就是要區分「
has-a
」與「is-a
」兩種關係的不同。
has-a
關係應當使用聚合關係描述,而只有
is-a
關係才符合繼承系統。
2、永遠不會出現需要將子類換成另乙個類的子類的情況。如果設計師不是很肯定乙個類會不會在將來變成另乙個類的子類的話,就不應當將這個類設計成當前這個超類的子類。
3、子類具有擴充套件超類的責任,而不是具有置換掉(
override
)或登出掉(
nullify
)超類的責任。如果子類需要大量地置換掉超類的行為,那麼這個子類不應當成為這個超類的子類。
4、只有在分類學角度上有意義時,才可以使用繼承,不要從工具類繼承。
迪公尺特法則:
又叫做最少知識原則:
least knowledge principle
,lkp
。乙個物件應當對其他物件有盡可能少的了解。
狹義的迪公尺特法則的缺點:
會在系統裡造出大量的小方法,散落在系統的各個角落。這些方法僅僅是傳遞間接的呼叫,因此與系統的商務邏輯無關。當設計師試圖從一張類圖看出總體的架構時,這些小的方法會造成迷惑和困擾。遵循類之間的迪公尺特法則會使乙個系統的區域性設計簡化,因為每乙個區域性都不會和遠距離的物件有直接的關聯。但是,這也會造成系統的不同模組之間的通訊效率降低,也會使系統的不同模組之間不容易協調。
迪公尺特法則的主要用意是控制資訊的過載。
在將迪公尺特法則運用到系統設計中時,要注意下面的幾點:
1、在類的劃分上,應當建立有弱耦合的類。
2、在類的結構設計上,每乙個類都應當盡量降低成員的訪問許可權(
accessibility)3、
在類的設計上,只要有可能,乙個類應當設計成不變類。
4、在對其他類的引用上,乙個物件對其他物件的引用應當降到最低。
廣義迪公尺特法則在類設計上的體現:
1、優先考慮將乙個類設定成不變類。
2、盡量降低乙個類的訪問許可權。
3、謹慎使用
serializable
。乙個類如果實現
serializable
介面的話,客戶端就可以將個類的例項序列化,然後再並行化。由於序列化和並行化涉及到類的內部結構,如果這個類的內部
private
結構在乙個新版本中發生變化的話,那麼客戶端可能會根據新版本的結構試圖將乙個老版本的序列化結果並行化,這回導致失敗。換言之,為防止這種情況發生,軟體提供商一旦將乙個類設定成為
serializable
的,就不能在新版本中修改這個類的內部結構,包括
private
的方法和句段。因此,除非絕對必要,不要使用
serializable。4、
盡量降低成員的訪問許可權。
Java設計模式學習筆記1
用最簡單加減法來舉例 calculate 計算方法介面 public inte ce calculate分別建立add以及sub子類並實現其邏輯 public class addimplements calculate public class subimplements calculate 建立c...
Java設計模式筆記(1)單例模式
單例模式 確保某乙個類只有乙個例項,而且自行例項化並向整個系統提供這個例項。package com.juno.singlepattern 餓漢式單例,通用 建議 public class singletonone public static singletonone getinstance publ...
JAVA與模式 設計原則筆記
設計原則 開 閉 原則 open close principle 或者ocp 目標 乙個軟體實體應該對擴充套件開發,對修改say no 在設計乙個模組的時候,應當思考日後公升級過程中,如何不修改源 的情況下改變這個模組的行為 黎克特制代換原則 liskov substitution principl...