1. 程式人生 > >C#中的擴充套件方法(向已有類新增方法,但無需建立新的派生型別)

C#中的擴充套件方法(向已有類新增方法,但無需建立新的派生型別)

擴充套件方法使你能夠向現有型別“新增”方法,而無需建立新的派生型別、重新編譯或以其他方式修改原始型別。 擴充套件方法是一種特殊的靜態方法,但可以像擴充套件型別上的例項方法一樣進行呼叫。 以上是msdn官網對擴充套件方法的描述,現在我通過一個情景例子來對此進行闡釋。假設一個控制檯程式class Program{}裡面的主函式如下:

複製程式碼
static void Main(string[] args)
        {
            DateTime now = DateTime.Now;
            string time = now.ToString("yyyy-MM-dd HH:mm:ss
"); Console.WriteLine(time); Console.ReadKey(); }
複製程式碼

假設需求變了,日期的顯示格式要變成"yyyy-MM-dd"這種格式,當然只需要初始化time時按下面寫法改寫即可:

string time = now.ToString("yyyy-MM-dd");

但是如果要改變日期格式的有很多個類呢?每個都要改一次嗎?這樣一旦需求變來變去就忙死人了。傳統的解決方式是封裝一個幫助類,在裡面寫方法,然後供其他類呼叫。

本例在當前專案模仿新增一個DateHelper類:public class DateHelper{}

,在類裡面定義方法:

public static string DateToString(DateTime dt)
        {
            return dt.ToString("yyyy-MM-dd HH:mm:ss");
        }

於是原來的主函式改寫如下:

複製程式碼
static void Main(string[] args)
        {
            DateTime now = DateTime.Now;
            string time = DateHelper.DateToString(now);
            Console.WriteLine(time);
            Console.ReadKey();
        }
複製程式碼

此時如果變需求,只需要改寫DateHelp類裡的DateToString()方法就行了,不管有多少個類呼叫此方法,都會被影響。問題解決了,可是這樣要呼叫另一個類的方法,還是有點麻煩,有沒有什麼方法能夠讓我們像now.DateToString()一樣直接呼叫呢?當然DateTime是微軟寫好的,我們改不了,無法建立想要的例項方法,於是,便引出了擴充套件方法。
下面是擴充套件方法的要素:

1.此方法必須是一個靜態方法

2.此方法必須放在靜態類中

3.此方法的第一個引數必須以this開頭,並且指定此方法是擴充套件自哪個型別

根據以上要素,我們DateHelper類改成靜態類:public static class DateHelper{} ,同時改寫DateToString()方法:

public static string DateToString(this DateTime dt)
        {
            return dt.ToString("yyyy-MM-dd HH:mm:ss");
        }

此時回到主函式方法體,輸入"now."便可以看見自動提示有個DateToString()方法,於是程式碼可以這樣寫:

複製程式碼
static void Main(string[] args)
        {
            DateTime now = DateTime.Now; 
            string time = now.DateToString();
            Console.WriteLine(time);
            Console.ReadKey();
        }
複製程式碼

顯而易見,這樣用起來會更加便捷,而且這樣讓我們看起來確實就像是被擴充套件型別本身具有的例項方法一樣,可讀性很高。下面概括一下擴充套件方法的特點:

1.擴充套件方法擴充套件自哪個型別,就必須是此型別的變數來使用,其他型別無法使用,本例擴充套件自DateTime型別,就只能是被DateTime型別的變數.出來(now.DateToString())
2.擴充套件方法中的this後面的引數不屬於方法的引數,本例是無引數,this後面的DateTime dt是指明擴充套件方法擴充套件自何種型別
3.如果擴充套件方法和例項方法具有相同的簽名,則優先呼叫例項方法
4.擴充套件自父類上的方法,可以被子類的物件直接使用
5.擴充套件自介面上的方法,可以被實現類的物件直接使用
6.擴充套件方法最終還是被編譯器編譯成:靜態類.靜態方法(),本例中now.DateToString()最終還是會被編譯成DateHelper.DateToString(now),這是它的本質

實際上,我們可能會遇到這樣的情景,如在介面擴充套件一個方法的時候,所有的原本已實現該介面的類都要實現新擴充套件的方法,這樣的改動是一個很麻煩的工作,可以使用擴充套件方法“曲線救國”;而有時候我們想為某個類新增新方法卻不想改動這個類,那麼擴充套件方法這種“偽新增”方法的方式就體現出它的價值了。最常見的擴充套件方法是LINQ標準查詢運算子,運用廣泛,這種方便快捷的方式理應博得碼農們點1024個贊。

不逆襲,不 I T !
Can't fly , can't be an IT guy ! 轉載自:http://www.cnblogs.com/0weibin/p/3954639.html