連載:物件導向葵花寶典:思想、技巧與實踐(33) - ISP原則

來源:互聯網
上載者:User

標籤:style   blog   java   color   使用   strong   

 ISP,Interface Segregation Principle,中文翻譯為“介面隔離原則”。


和DIP原則一樣,ISP原則也是大名鼎鼎的Martin大師提出來的,他在1996年的C++ Reporter發表“ The Interface Segregation Principle”的文章具體闡述了ISP原則,並且在他的經典著作《 Agile Software Development, Principles, Patterns》(中文翻譯為:敏捷式軟體開發 (Agile Software Development):原則、模式與實踐)、《Practices, and Agile Principles, Patterns, and Practices in C#》(中文翻譯為:敏捷式軟體開發 (Agile Software Development):原則、模式與實踐(C#版))中詳解了ISP原則。

 

ISP最原始的定義例如以下:

“CLIENTS SHOULD NOT BE FORCED TO DEPEND UPON INTERFACES THAT THEY DO NOT USE.”

翻譯成中文就是“client不應該被強迫去依賴它們並不須要的介面”。

 

單純從字面意思來看,ISP原則是5個原則中最好理解的一個了。可是我們深入思考一下,事實上發現也沒有那麼簡單。假設你還記得我們前面講的那些原則,你可能會想到一個問題:既然有了SRP,為什麼還要ISP?

 

如今我們來回憶一下SRP原則,假設類滿足了SRP原則,那麼基於這個類提煉的介面不就自然而然的滿足了ISP原則了嗎?為什麼我們還要費神費力的又搞一個ISP原則呢?

 

Martin大師自然不會是吃飽了沒事做,有益整個東東來折騰大家,他在ISP的論文中有這麼一句話交代了ISP原則,可惜的是非常多人都沒有把這句話貼出來:

The ISP acknowledges that there are objects that require non-cohesive interfaces;

however it suggests that clients should not know about them as a single class. Instead, clients

should know about abstract base classes that have cohesive interfaces.

翻譯一下:ISP原則承認對象須要非內聚的介面,然而ISP原則建議client不須要知道整個類,僅僅須要知道具有內聚介面的抽象父類就可以。

 

也就是說,ISP應用的情境是某些類不滿足SRP原則,但使用這些類的client(即調用的類)應該依據介面來使用它,而不是直接使用它

 

儘管翻譯了一下,但還是比較抽象,給個範例一看就明確了,並且已經有一個非常好的範例了,即SRP原則中的“一體機”。

 

在“一體機”的範例中,儘管“一體機”同一時候具備“列印、複印、掃描、傳真”的功能,但我們並不會設計一個“一體機”的介面,而是設計4個介面。這樣調用介面的類能夠依據自己須要精確使用某個介面,而不是調用一個大而全的介面。

 

具體代碼例如以下:

ICopier.java

package com.oo.java.principles.isp;/** * 複印機介面 */public interface ICopier {        /**     * 複印     * @param paper     */    void copy(Paper paper);}


IFaxMachine.java

package com.oo.java.principles.isp;/** * 傳真機介面 */public interface IFaxMachine {    /**     * 傳真     * @param msg     */    void fax(String msg);}

IPrinter.java

package com.oo.java.principles.isp;/** * 印表機介面 */public interface IPrinter {        /**     * 列印     * @param doc     */    void print(Document doc);}

IScanner.java

package com.oo.java.principles.isp;/** * 掃描器介面 */public interface IScanner {    /**     * 掃描     * @param paper     */    void scan(Paper paper);}

MultiFuncPrinter.java

package com.oo.java.principles.isp;/** * 多功能事務機(一體機) * 實現了IFaxMachine(傳真機)、ICopier(複印機)、IPrinter(印表機)、IScanner(掃描器)4個介面 * 而不是提供一個IMultiFuncPrinter的介面,同一時候提供以上介面的功能 * */public class MultiFuncPrinter implements IFaxMachine, ICopier, IPrinter, IScanner {    @Override    public void scan(Paper paper) {        // TODO Auto-generated method stub    }    @Override    public void print(Document doc) {        // TODO Auto-generated method stub    }    @Override    public void copy(Paper paper) {        // TODO Auto-generated method stub    }    @Override    public void fax(String msg) {        // TODO Auto-generated method stub    }}

People.java

package com.oo.java.principles.isp;/** * 人 */public class People {        /**     * 複印操作,copy方法依賴ICopier介面,而不是使用MutiFuncPrinter類     */    public void copy(ICopier copier, Paper paper){        copier.copy(paper);    }        /**     * 列印操作,print方法依賴IPrinter介面,而不是使用MutiFuncPrinter類     */    public void print(IPrinter printer, Document doc){        printer.print(doc);    }        /**     * 傳真操作,fax方法依賴IFaxMachine介面,而不是使用MutiFuncPrinter類     */    public void fax(IFaxMachine faxer, String message){        faxer.fax(message);    }        /**     * 掃描操作,scan方法依賴IScanner介面,而不是使用MutiFuncPrinter類     */    public void scan(IScanner scanner, Paper paper){        scanner.scan(paper);    }}

Tester.java

package com.oo.java.principles.isp;public class Tester {    public static void mai(String args[]){        People people = new People();        MultiFuncPrinter mfp = new MultiFuncPrinter();                //例如以下函數都是使用mfp作為參數,但實際上是使用了MultiFuncPrinter類實現了的不同介面        people.copy(mfp, new Paper());     //使用了MultiFuncPrinter類的ICopier介面,        people.fax(mfp, "I love oo");      //使用了MultiFuncPrinter類的IFaxMachine介面,        people.print(mfp, new Document()); //使用了MultiFuncPrinter類的IPrinter介面,        people.scan(mfp, new Paper());     //使用了MultiFuncPrinter類的IScanner介面,    }}





聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.