接口隔離原則:客戶端不應該依賴它不需要的接口;一個類對另一個類的依賴應該建立在最小的接口上。
接口隔離不應該繼承臃腫的接口,只依賴需要的接口,接口必須實現單一職責原則,
舉個簡單的例子:
1 public class B : A 2 { 3 public void Method1() 4 { 5 Console.WriteLine("需要用到方法1"); 6 } 7 8 public void Method2() 9 { 10 throw new NotImplementedException(); 11 } 12 13 public void Method3() 14 { 15 Console.WriteLine("需要用到方法3"); 16 } 17 18 public void Method4() 19 { 20 Console.WriteLine("需要用到方法4"); 21 } 22 23 public void Method5() 24 { 25 throw new NotImplementedException(); 26 } 27 } 28 29 public class C : A 30 { 31 public void Method1() 32 { 33 Console.WriteLine("需要用到方法1"); 34 } 35 36 public void Method2() 37 { 38 Console.WriteLine("需要用到方法2"); 39 } 40 41 public void Method3() 42 { 43 throw new NotImplementedException(); 44 } 45 46 public void Method4() 47 { 48 throw new NotImplementedException(); 49 } 50 51 public void Method5() 52 { 53 Console.WriteLine("需要用到方法5"); 54 } 55 } 56 57 58 59 public interface A 60 { 61 void Method1(); 62 void Method2(); 63 void Method3(); 64 65 void Method4(); 66 void Method5(); 67 68 }
從上面的例子我們可以看到,B需要用到A接口的Method1,Method3,Method4方法,C需要用到A接口的Method1,Method2,Method5方法,B和C類繼承的A接口都有不需要用到的接口方法,造成臃腫。
根據接口隔離原則,當一個接口太大時,需要將它分割成一些更細小的接口,使用該接口的客戶端僅需制定與之相關的方法就可以了。每一個接口應該承擔一種相對獨立的角色。這裏的接口有兩種不同的含義:一種是指一個類型所具有的方法特徵的集合,僅僅是一種邏輯上的抽象;另一種是指某種語言具體的接口定義,有嚴格的定義和結構,比如Java語言中的interface。對於這兩種不同的含義,ISP的表達方式以及含義都有所不同。
我們來對上面的例子通過實現接口隔離原則進行二次改造:
1 public class B : A1 2 { 3 public void Method1() 4 { 5 Console.WriteLine("需要用到方法1"); 6 } 7 8 public void Method3() 9 { 10 Console.WriteLine("需要用到方法3"); 11 } 12 13 public void Method4() 14 { 15 Console.WriteLine("需要用到方法4"); 16 } 17 18 } 19 20 public class C : A2 21 { 22 public void Method1() 23 { 24 Console.WriteLine("需要用到方法1"); 25 } 26 27 public void Method2() 28 { 29 Console.WriteLine("需要用到方法2"); 30 } 31 32 public void Method5() 33 { 34 Console.WriteLine("需要用到方法5"); 35 } 36 } 37 38 39 40 public interface A 41 { 42 void Method1(); 43 44 } 45 46 public interface A1:A 47 { 48 void Method3(); 49 void Method4(); 50 } 51 52 53 public interface A2 : A 54 { 55 void Method2(); 56 void Method5(); 57 }