2017-03-08 71 views
1

我還沒有看到接口實現爲類成員之前。有人可以解釋發生了什麼嗎?你允許實例化一個接口嗎?這些接口所需的方法在哪裏實現?爲什麼這種接口在課堂上以這種方式實現?

public class MyClass 
{ 
    private readonly ITest1 interface1; 
    private readonly ITest2 interface2; 
    private readonly ITest3 interface3; 

    public MyClass(ITest1 interface1, ITest2 interface2, ITest3 interface3) 
    { 
     this.interface1 = interface1; 
     this.interface2 = interface2; 
     this.interface3 = interface3; 
    } 

    public void TestMethod() 
    { 
     var lines = interface1.GetData(); 
     var file = interface2.Parse(lines); 
     interface3.Copy(file); 
    } 
} 

什麼是比我有常用的接口方式的不同:

public class Person : IEquatable<Dog> 
{ 
    public int Age { get; set; } 

    public bool Equals(Dog d) 
    { 
     if (d.Age == this.Age) 
      return true; 
     else 
      return false; 
    } 
} 

public class Dog 
{ 
    public int Age { get; set; } 
} 
+5

無意冒犯,但我覺得你真的需要去通過C#的一些教程運行,具體怎麼接口工作。 – DavidG

+0

我還沒找到解釋第一個例子的東西。我發現的所有東西都與第二個例子類似。 – eek142

+0

他們沒有實例化接口,他們使用實例(像往常一樣),但它響應給定的接口 - 這意味着他們實現了它定義的方法 - 但實現不在接口 –

回答

3

的區別是:

您與Person類完成什麼是接口實現

MyClass沒有實現任何接口,但它接受接口作爲構造函數參數。調用構造函數的人將提供實現接口的實例。更多以下內容。

你允許實例化一個接口嗎?

NO。實現接口的類將被實例化。

這些接口所需方法的實現在哪裏?

當這個人創建你的類的實例時,他們將傳遞實現該接口的類的實例。就像這樣:

public interface ITest1 
{ 
    string GetData(); 
} 
public class Test1 : ITest1 
{ 
    public string GetData() 
    { 
     return "Data"; 
    } 
} 

他們會叫你的類是這樣的:

var test1 = new Test11(); 

// instead of nulls it will be other instances like test1 
var myClass = new MyClass(test1, null, null); 

我還沒有看到爲類成員之前實現的接口。有人可以解釋發生了什麼嗎?

這是怎麼回事我已經用上面的例子解釋過了。

這實際上是一種非常常見的方式,是的,還有其他方式,但這是其中一種方式。

優勢

  1. 這樣你MyClass不知道什麼具體類型將被通過,但它知道什麼具體類型,它會支持的接口。

  2. MyClass裏面,你只有依賴於接口的代碼,所以你的類是鬆耦合的。

  3. 依賴注入可用於注入依賴關係到MyClass的構造函數中。這就是所謂的構造函數注入。

什麼是比我正常使用的接口方式的不同:

沒有區別。但是你需要考慮人們如何使用這個班。例如,如果你想使用MyClass,你會做這是你習慣什麼來:

public class Test1 : ITest1 
{ 
    public string GetData() 
    { 
     return "Data"; 
    } 
} 

爲了澄清更進一步,想象MyClass有另一個構造和現場像這樣:

private readonly IEquatable<Dog> iEq; 
public MyClass(IEquatable<Dog> iEq) { this.iEq = iEq; } 

然後,您可以使用Person類的實例調用它。所以它沒有什麼不同。

注意:沒有人會很樂意被等同於一隻狗;)

+0

這是有道理的。基本上,接口只是代表實現該合同的任何類。這就是我所困惑的。正如你所說,只要它實現了接口,你傳入的具體類型並不重要。謝謝! – eek142

+0

你明白了。很高興幫助並清除混淆。 – CodingYoshi

1

無法實例的接口;一個派生類將被傳遞給構造函數。

,所以你將有一些類:

​​

,並利用它們是這樣的:

var a = new A(); 
var b = new B(); 
var c = new C(); 
var mc = new MyClass(a, b, c); 
mc.TestMethod(); 
1

你不能實例化的界面,你可以用他的繼承類型更換接口!

這是接口的正常使用(你的例子):

public class MyClass 
{ 
    public MyClass(ITest1 interface1, ITest2 interface2, ITest3 interface3) 
    { 
     this.interface1 = interface1; 
     this.interface2 = interface2; 
     this.interface3 = interface3; 
    } 

    public void TestMethod() 
    { 
     var lines = interface1.GetData(); 
     var file = interface2.Parse(lines); 
     interface3.Copy(file); 
    } 

    private readonly ITest1 interface1; 
    private readonly ITest2 interface2; 
    private readonly ITest3 interface3; 
} 

您已經創建了MyClass類三個方面:接口1,接口2和接口3。

通過類的構造函數,可以注入ITest1ITest2ITest3的實例。這些實例應該是一些實現適當接口的類。

實施例:

可以實現接口和在下面的例子中提供類似的對象:

public class Test1 : ITest1 
{ 
    public string GetData() 
    { 
     // code 
    } 
} 

public class Test2 : ITest2 
{ 
    public string GetData() 
    { 
     // code 
    } 
} 

public class Test3 : ITest3 
{ 
    public string GetData() 
    { 
     // code 
    } 
} 

創建MyClass的實施例將是:

var test1 = new Test1(); 
var test2 = new Test2(); 
var test3 = new Test3(); 
var myClass = new MyClass(test1, test2, test2); 

對象test1test2test3實現接口ITest1ITest2ITest3

結論

有沒有神奇。 接口被其繼承類型的類型替換!基本上,您在代碼中提供了抽象的實現。