1. 單一職責原則(Single Responsibility Principle)post
每個類應該專一於作一件事情。設計
2. 里氏替換原則(Liskov Substitution Principle)對象
超類存在的地方,子類是能夠替換的。blog
3. 依賴倒置原則(Dependence Inversion Principle)繼承
實現儘可能依賴抽象,不依賴具體實現。接口
4. 接口隔離原則(Interface Segregation Principle)
應當爲客戶端提供儘量小的單獨的接口,而不是提供大的總的接口。
5. 迪米特法則(Law Of Demeter)
又叫最少知識原則,一個軟件實體應當儘量少的與其餘實體發生相互做用。
6. 開閉原則(Open Close Principle)
面向擴展開放,面向修改關閉。
7. 組合/聚合複用原則(Composite/Aggregate Reuse Principle CARP)
儘可能使用合成/聚合達到複用,儘可能少用繼承。原則: 一個類中有另外一個類的對象。
細則
單一職責原則(Single Responsibility Principle)
由於:
能夠下降類的複雜度,一個類只負責一項職責,其邏輯確定要比負責多項職責簡單的多;提升類的可讀性,提升系統的可維護性;變動引發的風險下降,變動是必然的,若是單一職責原則遵照的好,當修改一個功能時,能夠顯著下降對其餘功能的影響。須要說明的一點是單一職責原則不僅是面向對象編程思想所特有的,只要是模塊化的程序設計,都適用單一職責原則。
因此:
從大局上看Android中的Paint和Canvas等類都遵照單一職責原則,Paint和Canvas各司其職。
里氏替換原則(Liskov Substitution Principle)
由於:
里氏替換原則告訴咱們,在軟件中將一個基類對象替換成它的子類對象,程序將不會產生任何錯誤和異常,反過來則不成立,若是一個軟件實體使用的是一個子類對象的話,那麼它不必定可以使用基類對象。里氏替換原則是實現開閉原則的重要方式之一,因爲使用基類對象的地方均可以使用子類對象,所以在程序中儘可能使用基類類型來對對象進行定義,而在運行時再肯定其子類類型,用子類對象來替換父類對象。
因此:
使用里氏替換原則時須要注意,子類的全部方法必須在父類中聲明,或子類必須實現父類中聲明的全部方法。儘可能把父類設計爲抽象類或者接口,讓子類繼承父類或實現父接口,並實如今父類中聲明的方法,運行時,子類實例替換父類實例,咱們能夠很方便地擴展系統的功能,同時無須修改原有子類的代碼,增長新的功能能夠經過增長一個新的子類來實現。
從大局看Java的多態就屬於這個原則。
依賴倒置原則(Dependence Inversion Principle)
由於:
具體依賴抽象,上層依賴下層。假設B是較A低的模塊,但B須要使用到A的功能,這個時候,B不該當直接使用A中的具體類;而應當由B定義一抽象接口,並由A來實現這個抽象接口,B只使用這個抽象接口;這樣就達到了依賴倒置的目的,B也解除了對A的依賴,反過來是A依賴於B定義的抽象接口。經過上層模塊難以免依賴下層模塊,假如B也直接依賴A的實現,那麼就可能形成循環依賴。
因此:
採用依賴倒置原則能夠減小類間的耦合性,提升系統的穩定性,減小並行開發引發的風險,提升代碼的可讀性和可維護性。
從大局看Java的多態就屬於這個原則。
接口隔離原則(Interface Segregation Principle)
由於:
提供儘量小的單獨接口,而不要提供大的總接口。暴露行爲讓後面的實現類知道的越少越好。譬如類ProgramMonkey經過接口CodeInterface依賴類CodeC,類ProgramMaster經過接口CodeInterface依賴類CodeAndroid,若是接口CodeInterface對於類ProgramMonkey和類CodeC來講不是最小接口,則類CodeC和類CodeAndroid必須去實現他們不須要的方法。將臃腫的接口CodeInterface拆分爲獨立的幾個接口,類ProgramMonkey和類ProgramMaster分別與他們須要的接口創建依賴關係。也就是採用接口隔離原則。
因此:
創建單一接口,不要創建龐大的接口,儘可能細化接口,接口中的方法儘可能少。也就是要爲各個類創建專用的接口,而不要試圖去創建一個很龐大的接口供全部依賴它的類去調用。依賴幾個專用的接口要比依賴一個綜合的接口更靈活。接口是設計時對外部設定的約定,經過分散定義多個接口,能夠預防外來變動的擴散,提升系統的靈活性和可維護性。
從大局來講Java的接口能夠實現多繼承就是接口隔離原則的基礎保障。
迪米特法則(Law Of Demeter)
由於:
類與類之間的關係越密切,耦合度也就愈來愈大,只有儘可能下降類與類之間的耦合才符合設計模式;對於被依賴的類來講,不管邏輯多複雜都要儘可能封裝在類的內部;每一個對象都會與其餘對象有耦合關係,咱們稱出現成員變量、方法參數、方法返回值中的類爲直接的耦合依賴,而出如今局部變量中的類則不是直接耦合依賴,也就是說,不是直接耦合依賴的類最好不要做爲局部變量的形式出如今類的內部。
因此:
一個對象對另外一個對象知道的越少越好,即一個軟件實體應當儘量少的與其餘實體發生相互做用,在一個類裏能少用多少其餘類就少用多少,尤爲是局部變量的依賴類,能省略儘可能省略。同時若是兩個類沒必要彼此直接通訊,那麼這兩個類就不該當發生直接的相互做用。若是其中一個類須要調用另外一個類的某一方法的話,能夠經過第三者轉發這個調用。
從大局來講Android App開發中的多Fragment與依賴的Activity間交互通訊遵照了這一法則。
開閉原則(Open Close Principle)
由於:
開放封閉原則主要體如今對擴展開放、對修改封閉,意味着有新的需求或變化時,能夠對現有代碼進行擴展,以適應新的狀況。軟件需求老是變化的,世界上沒有一個軟件的是不變的,所以對軟件設計人員來講,必須在不須要對原有系統進行修改的狀況下,實現靈活的系統擴展。
因此:
能夠經過Template Method模式和Strategy模式進行重構,實現對修改封閉,對擴展開放的設計思路。
封裝變化,是實現開放封閉原則的重要手段,對於常常發生變化的狀態,通常將其封裝爲一個抽象,拒絕濫用抽象,只將常常變化的部分進行抽象。
組合/聚合複用原則(Composite/Aggregate Reuse Principle CARP)
由於:
其實整個設計模式就是在講如何類與類之間的組合/聚合。在一個新的對象裏面經過關聯關係(包括組合關係和聚合關係)使用一些已有的對象,使之成爲新對象的一部分,新對象經過委派調用已有對象的方法達到複用其已有功能的目的。也就是,要儘可能使用類的合成複用,儘可能不要使用繼承。
若是爲了複用,便使用繼承的方式將兩個不相干的類聯繫在一塊兒,違反里氏代換原則,哪是生搬硬套,忽略了繼承了缺點。繼承複用破壞數據封裝性,將基類的實現細節所有暴露給了派生類,基類的內部細節經常對派生類是透明的,白箱複用;雖然簡單,但不安全,不能在程序的運行過程當中隨便改變;基類的實現發生了改變,派生類的實現也不得不改變;從基類繼承而來的派生類是靜態的,不可能在運行時間內發生改變,所以沒有足夠的靈活性。
因此:
組合/聚合複用原則可使系統更加靈活,類與類之間的耦合度下降,一個類的變化對其餘類形成的影響相對較少,所以通常首選使用組合/聚合來實現複用;其次才考慮繼承,在使用繼承時,須要嚴格遵循里氏代換原則,有效使用繼承會有助於對問題的理解,下降複雜度,而濫用繼承反而會增長系統構建和維護的難度以及系統的複雜度,所以須要慎重使用繼承複用。