引言
委託是一個類,它定義了方法的類型,使得可以將方法當作另一個方法的參數來進行傳遞,這種將方法動態地賦給參數的做法,可以避免在程式中大量使用If-Else(Switch)語句,同時使得程式具有更好的可擴展性。
委託初識
我們知道委託是一個引用類型,所以它具有引用類型所具有的通性。它保存的不是實際值,而是保存對存儲在託管堆(managed heap)中的對象的引用。那它保存的是對什麼的引用呢?委託保存的是對函式(function)的引用。
對學過C/C++的人,是不是覺得跟函式指針很像呢!委託可以引用實例和靜態(在 Visual Basic 中為 Shared)方法,而函式指針只能引用靜態方法。 其實它們是有區別的,在非託管C/C++中,函式的地址就是一個記憶體地址。該地址不會攜帶任何額外的信息,例如函式期望的參數個數、參數類型、函式的返回值類型及函式的調用約定。總之,非託管C/C++中函式指針是非類型安全的。而.NET中的委託是類型安全的,委託會檢測它所保存的函式引用是否和聲明的委託匹配。
委託本質
在C#中使用delegate關鍵字定義委託,然後使用我們熟悉的函式調用的語法來調用委託,如上述例子中的cb(“skynet”,23)。在這簡單的表象背後,.NET編譯器為我們做了什麼呢?
可以知道定義CallBack委託時,編譯器為我們做了如下工作,實際上定義任何委託編譯器都會做如下工作:
聲明一個類,對應上圖中的.class nested public auto ansi sealed。
該類擴展自System.MulticastDelegate,對應上圖中的extends [mscorlib]System.MulticastDelegate。
該類包含一個構造器,對應上圖中的.ctor: void(object ,native int)。
該類包含三個方法,分別是BeginInvoke、EndInvoke、Invoke。
委託類
當我們用delegate關鍵字聲明委託時,編譯器自動為我們生成類。類的名字即為委託變數名,訪問類型為定義的委託訪問類型。如上例中,public delegate void CallBack(string name, int number);定義的委託對應的類為CallBack,訪問類型為public,該類繼承自[mscorlib]System.MulticastDelegate。如果我們定義委託的訪問類型為private或者protected,則對應的委託類的訪問類型為private或者protected。但是任何委託都繼承自[mscorlib]System.MulticastDelegate。
什麼是委託
首先要知道什麼是委託,用最通俗易懂的話來講,你就可以把委託看成是用來執行方法(函式)的一個東西。
如何使用委託
在使用委託的時候,你可以像對待一個類一樣對待它。即先聲明,再實例化。只是有點不同,類在實例化之後叫對象或實例,但委託在實例化後仍叫委託。