2009-07-16 31 views
3

我有點困惑,我知道代表就像函數指針一樣,它們用來將函數作爲參數傳遞給方法。.NET委託用於事件嗎?

這怎麼符合事件模型?

呼喚:

myButton.OnClick += new .....(); 

是在內部只是路過的方法/函數的參數在事件發生時,所有的用戶都收到該事件?

回答

10

看一看這個

Curiosity is bliss

+0

+1 - 良好的鏈接。 – 2009-07-16 13:16:58

+0

好博客。我真的很喜歡Julien Couvreur。 – Kredns 2009-07-16 17:05:26

+0

非常感謝,偉大的博客 – 2012-04-15 12:09:53

1

的事件,在點擊一個按鈕的情況下是「點擊」事件中,充當「函數指針」在這裏。意思是,當你使用+ =語法向你的方法添加你的方法時,你基本上將點擊函數指針指向你的函數。因此,點擊按鈕時,點擊功能指針將調用其指向的所有功能。說得通?

2

該事件有兩個操作符;添加和刪​​除。當你添加一個事件處理程序(如你的例子)時,事件將獲得對該方法的引用,並將其添加到訂閱事件處理程序的列表中。當事件發生時,它將通過列表並調用其中的方法。

3

當你這樣做:

myButton.OnClick += new ...(); 

你將你的委託作爲一個用戶到該事件。當事件在晚些時候被提出時,所有訂戶都會被調用(沒有關於訂單的保證)。這被稱爲多播委託。它有點像一個函數指針,它允許它「指向」多個函數。

注意,現在你不需要明確創建委託,你可以只使用方法名:

myButton.OnClick += MethodName; 

而且不要忘了,你可以(也應該看到why)取消訂閱您訂閱事件,以防止泄漏:

myButton.OnClick -= MethodName; 
0

按鈕有一個私人「多播委託」字段和公共財產,如「點擊」您使用+ =和 - =運營商是一個自動生成的方式管理該私人領域的狀態。

當按鈕內部引發Click事件,則調用私有多播委託,將調用一切,它目前所知道的代表。


該系統可能會造成混淆第一個實現自己的活動的時候,因爲相同的標識符,「事件名稱」,指的是你的類中的一件事(私有多播委託場)和類之外的另一件事(該領域的公共管理機制)。

1

事件是基於委託的屬性。

它包裝一個私人(和隱藏)代表成員。

2

確實,代表非常像函數指針。 第一個區別在於委託由2個「指針」組成:一個函數指針和一個實例指針。毫不奇怪,Delegate類具有以下兩個屬性:

// Gets the method represented by the delegate. 
public MethodInfo Method { get; } 

// Gets the class instance on which the current delegate 
// invokes the instance method. 
public object Target { get; } 

第二區別是.NET代表可以是組播。可以在一個MulticastDelegate中添加兩個代表。也可以從多播委託中刪除委託。被調用時,多播委託將調用其所有子委託。這可能會導致其他問題,但我會偏離最初的問題。


一種事件,在另一方面,是完全不同的東西。事實上,一個事件是一個有特殊訪問者的財產。常規屬性有這兩個訪問者:得到集合。事件有這兩個:刪除

add accessor將當前委託與新委託組合到一個多播委託中。刪除訪問者將做相反的事情。

有考慮到這一點,這是很容易理解爲什麼C#設計人員挑選了+ =- =運營商。我的意思是,以下兩行有些相同(如果你忽略第二個這樣的事實)。

myButton.OnClick += newEventHandler; 
myButton.OnClick = myButton.OnClick + newEventHandler; 
0

'event'是一個多播委託。 例如:

INotifyPropertyChanged的的
public class ObservableObject : INotifyPropertyChanging, INotifyPropertyChanged 
{ 
    public event PropertyChangedEventHandler PropertyChanged; 
} 

實現器包括public event PropertyChangedEventHandler PropertyChanged。 PropertyChangedEventHandler是一個代表聲明爲:

public delegate void PropertyChangedEventHandler(object sender, PropertyChangedEventArgs e); 

那麼這個修飾符事件在做什麼? 首先只有包含的實例可以調用它。 第二個客戶端只能向/從實例中添加/刪除處理程序。

編譯器添加了兩個方法add_PropertyChanged和remove_PropertyChanged 編譯器將該成員標記爲私有。

0

我同意所有的說法,我只是想補充我的兩分錢。

如果我重新寫的文檔我要說的是, 代表是語言的指針和部分 而事件是一個框架,允許您使用的儀器的一部分,Windows的事件 - 和 - 消息泵。您在嘗試在ASP.NET下使用EVENTS時需要注意這一點,並且需要等待事件。 (欲瞭解更多信息,請致電http://discuss.joelonsoftware.com/default.asp?joel.3.456478.15) 我的問題是MultiCast Delegates是中間的一些版本,所以很難區分並清除它們。

委託是指向一個功能 MultiCastdelegate下一個名字聚集委託列表

事件是做一些不同的事情呼叫者的ThreadContext下 1.奔跑(見BackgroundWorker的和修正AsyncOperationManager)。 2.事件可以被添加到接口(澄清OO連接)

委託收聽者的上下文下 1.奔跑 2.不能被添加到接口

http://blogs.msdn.com/b/jaybaz_ms/archive/2004/06/17/158636.aspx閱讀有關事件和多個數據一般的競賽條件。