2012-01-04 57 views
4

我熟悉接口僅包含方法,委託或事件的簽名這一事實。方法的實現在實現接口的類中完成。實現接口的類必須實現它的方法。瞭解ICollection實現和接口

我創建了一個通用列表。當我瀏覽List的聲明時,我看到它繼承了ICollection,並且ICollection具有一個簽名方法:object SyncRoot {get; } 爲什麼我看不到List類中的SyncRoot實現?

public class List<T> : IList<T>, ICollection<T>, IEnumerable<T>, 
         IList, ICollection, IEnumerable 
{ 
    public List(); 
    public List(IEnumerable<T> collection); 
    public List(int capacity); 
} 

我期望在上面看到:public object syncRoot()?另外,如果我用JustDecompile(Telerik)打開它,我會看到它被實現,但是作爲private。我錯過了什麼?

+4

http://stackoverflow.com/questions/143405/c-interfaces-implicit-and-explicit-implementation – dtb 2012-01-04 15:59:03

+0

鯊魚,你是什麼意思? 0%意味着什麼? – user829174 2012-01-04 16:01:46

+3

詢問10個問題後0%的接受程度非常差。請重新訪問您之前的一些問題,然後點擊您認爲合適,寫得很好或有幫助的答案旁邊的「打勾」。 – ColinE 2012-01-04 16:01:46

回答

6

這是@dtb指出的顯式接口實現。這意味着,如果從ICollection類型的參考,但不用於從List

var l = new List<int>(); 

// compiler error 
var sr1 = l.SyncRoot; 

ICollection c = l; 

// works 
var sr2 = c.SyncRoot; 

類型的引用這是顯式接口實現的功率成員SyncRoot可見。如果出於某種原因想要定義接口引用的基本行爲,但是需要爲您的類引用定義專門的行爲(例如,將返回類型更改爲更具體,通常無法在簡單的重載中生效),您可以執行這個。或者,如果您想爲傳統目的實現接口,但希望隱藏在實現中不再有用的方法或屬性。

因此,如果你看一下反編譯的代碼,你會看到這樣的聲明:

object ICollection.SyncRoot 
{ 
    ... 
} 

所以這個實現SyncRootICollection接口,使其可見通過任何ICollection參照List<T>對象,但隱藏它的任何其他(非ICollection)對List<T>對象的引用。

當使用像IEnumerable這樣的傳統接口時,這也非常有用。例如,如果您想要支持IEnumerable<T>,您還必須支持IEnumerable,但它們都有GetEnumerator()方法因返回類型而異。例如:

public class MySpecialList<T> : IEnumerable<T> 
{ 
    // if we access from any other reference, we get the new, generic 
    // interface 
    public IEnumerator<T> GetEnumerator() 
    { 
     // your actual implementation 
    } 

    // so if we access from a reference of IEnumerable, we get older, 
    // non-generic interface 
    IEnumerator IEnumerable.GetEnumerator() 
    { 
     return GetEnumerator(); 
    } 
} 

因爲我們不能有兩個方法,返回不同的值,但有相同的簽名(重載),我們可以告訴類GetEnumerator()意味着一件事與IEnumerable遺留引用時,有什麼東西完全不同的(更好)的所有其他引用:

var x = new MySpecialList<int>(); 
IEnumerable y = x; 

// returns the generic enumerator 
var genericEnum = x.GetEnumerator(); 

// since called from an IEnumerable, gets legacy enumerator 
var legacyEnum = y.GetEnumerator(); 
+0

這個我知道,我的問題是爲什麼我不能在列表中看到它的實現。 畢竟,List 繼承自ICollection,我應該在班級列表(F12)中看到它,不是嗎? – user829174 2012-01-04 16:04:28

+1

@ user829174:因爲它是私人的。它只能通過「ICollection」參考 – 2012-01-04 16:05:49

+0

@ user829174看到,你在哪裏看? – nos 2012-01-04 16:06:19