2013-10-02 118 views
6

擴展方法和靜態方法有什麼區別?擴展方法和靜態方法有什麼區別?

我有兩個類是這樣的:

public static class AClass { 
    public static int AMethod(string ....) 
    { 
    } 
} 

public static class BClass { 
    public static int BMethod(this string ....) 
    { 
    } 
} 

我可以用這些像

AClass.AMethod('...'); 

'...'.BMethod(); 

哪個建議?

回答

27

擴展方法仍然是一種靜態方法。你可以像使用普通靜態方法一樣使用它。

唯一的區別是,一個擴展方法可以讓你使用的方法中,看起來像它的零件種類的方式,所以你可以寫:

int result = stringValue.BMethod(); 

相反的:

int result = BClass.BMethod(stringValue); 

這個工作純粹是作爲一個編譯「技巧」 - 編譯器會看到第一個表單,並且如果BClass可用(它有一個合適的using並位於引用程序集中),那麼它會將其轉換爲第二個方法的IL您。這純粹是一種方便。

哪個建議?

這真的取決於。如果你控制類型,我建議把方法放在類型本身上。這通常更易於維護。

如果您不控制類型,或者您試圖「擴展」普通類型(如IEnumerable<T>),那麼擴展方法可能是一種合理的方法。但是,如果類型是一種非常常見的類型,我通常會避免使用擴展方法,因爲它們在智能感知中變成了「噪音」,這反過來會造成額外的混淆。例如,我個人不建議在System.ObjectSystem.String等上添加擴展方法。

+2

非常好(一如既往),裏德。 +1 – Brian

1

您不能覆蓋擴展方法。 只有當方法具有不同的簽名時,纔可以重載。

當然還有一些限制: 擴展方法必須作爲靜態方法和靜態類(在非嵌套的非泛型靜態類中更加精確)實現。 您可以使用擴展方法來擴展類或接口,但不能覆蓋它們。與接口或類方法具有相同名稱和簽名的擴展方法永遠不會被調用。在編譯時,擴展方法總是比類型本身定義的實例方法具有更低的優先級。 擴展方法無法訪問它們正在擴展的類型中的私有變量。 您可以將擴展方法視爲一種「合法」方式,以將更多靜態方法添加到現有類中,而無需實際繼承它們。 但有趣的是,與類的常規靜態方法不同,您無法在類級別上調用擴展方法(如果您嘗試此操作,將得到編譯時錯誤),而是必須在類的實例上調用它們(就好像它們是該類實例的一些常規方法,它們不是!!!)。

此外,在擴展方法內部,您可以自由使用在其上調用方法的傳遞對象實例的公共屬性,但決不僅限於靜態對象數據。只有擴展方法是靜態方法,但調用的對象是完整的常規對象實例。

相關問題