委託時一種特殊的類型,它用來保存方法的地址,這樣咱們很方便的調用方法,像變量同樣傳遞,回調。數組
C++中的函數指針也是保存方法的地址,可是有一點不同的是定義委託的時候就知道了它裏面能夠保存什麼樣的方法,而函數指針就沒有這些安全
因此委託相對更明確一點,更安全一點。函數
public delegate void MyDelegate(int x) //這樣的委託類型表示,該委託能夠用來保存無返回值,切參數爲int類型的方法
固然當咱們寫出上面那段代碼的時候,實際上編譯器作了其餘一些事,實際可能定義像下面這樣的spa
public class MyDelegate:system.MusticastDelegate { public MyDelegate(object obj,IntPtr method){……} //obj保存,方法的實例(靜態方法則null),IntPtr保存方法地址 public virtual void Invoke(int value){……} //調用方法 ……//省略 }
MusticastDelegate 內部有指針
_target字段 //保存當前委託保存方法,要使用的實例code
_methodPtr字段 //保存委託保存的方法對象
_invoalcationList字段 //保存委託鏈(若是隻有一個委託就Null)blog
public class MyClass{ Public void Method1(int y){ } public static void Method2(int y){ } }
一、當咱們使用MyDelegate del = new MyDelegate(new MyClass().Method1);get
那麼del對象中_target則保存了new MyClass()實例編譯器
_methodPtr保存了Method1地址
_invoalcationList此時爲NULL,由於只有一個委託
當咱們調用del(10),其實是調用del.Invoke(10) 而後Invoke執行的是_target._methodPtr(10)
二、當咱們使用MyDelegate del2 = new MyDelegate(MyClass.Method2);
那麼del2對象中_target則保存了NULL,由於是保存靜態方法,因此沒有對象
_methodPtr保存了Method2地址
_invoalcationList此時爲NULL,由於只有一個委託
當咱們調用del2(10),其實是調用del2.Invoke(10) 而後Invoke執行的是_target._methodPtr(10) 由於_target是null,因此實際是MyClass._methodPtr
三、del+=del2
那麼實際是執行了del = Delegate.Combine(del,del2)
內部是建立了_invoalcationList數組,裏面包含有兩個委託del,del2
_target =null
_methodPtr =Method2地址
當咱們調用del(10)時發現_invoalcationList裏面有兩個委託,則循環這個數組,分別調用每一個委託