我在閱讀這個 http://msdn.microsoft.com/en-us/library/bb882534.aspx如何使用自定義事件訪問在C#中添加事件時要調用的方法?
目前還不清楚我該怎麼做。
更新:由於一些人已經回答了這些主持人如何假裝問題是含糊!
我在閱讀這個 http://msdn.microsoft.com/en-us/library/bb882534.aspx如何使用自定義事件訪問在C#中添加事件時要調用的方法?
目前還不清楚我該怎麼做。
更新:由於一些人已經回答了這些主持人如何假裝問題是含糊!
這裏是你如何處理自定義事件訪問一個簡單的例子,我知道你是想每一個事件處理程序附加時間/從事件分開來調用一個函數。在這種情況下,你需要創建下面的代碼的私人後盾代表myCustomEventDelegate
,並讓您的自定義事件訪問add/remove
塊添加/刪除處理程序委託,當然調用您的附加功能。
在這個例子中,我只是寫入控制檯,當然如果你的代碼是一個庫的一部分,那麼這可不是一個好主意,它可能用於不同類型的應用程序,而這些應用程序可能無法訪問控制檯,但它畢竟只是一個例子。
using System;
namespace CustomEventDemo
{
class Program
{
static void Main(string[] args)
{
TheClassExposingYourEvent instance = new TheClassExposingYourEvent();
instance.MyCustomEvent += new EventHandler<EventArgs>(Program_MyCustomEvent);
instance.DoSomething();
instance.MyCustomEvent -= new EventHandler<EventArgs>(Program_MyCustomEvent);
Console.ReadKey();
}
static void Program_MyCustomEvent(object sender, EventArgs e)
{
Console.WriteLine("The event was fired");
}
}
class TheClassExposingYourEvent
{
private EventHandler<EventArgs> _myCustomEventDelegate;
public event EventHandler<EventArgs> MyCustomEvent
{
add
{
_myCustomEventDelegate += value;
// Do something extra here.
// Writing to the console is a bad example!!!
Console.WriteLine("Event handler attached");
}
remove
{
_myCustomEventDelegate -= value;
// Do something extra here.
// Writing to the console is a bad example!!!
Console.WriteLine("Event handler detached");
}
}
public void DoSomething()
{
if (_myCustomEventDelegate != null)
{
_myCustomEventDelegate(this, EventArgs.Empty);
}
}
}
}
非常感謝你會閱讀其他答案,看看哪一個最適合我。 – user310291 2011-04-23 18:47:21
難道不是這樣嗎?
event EventHandler IDrawingObject.OnDraw
{
add
{
lock (PreDrawEvent)
{
PreDrawEvent += value;
}
YourFunction(); // HERE
}
這就是我的想法。 – user310291 2011-04-23 18:48:18
事件實際上是通過添加/刪除訪問器進行封裝以限制外部類如何修改委託的非公開委託。下面的代碼雖然冗長,但詳細解釋了代表和事件。它來自我爲同事試圖學習.Net的一個示例項目。像書一樣從上到下閱讀(註釋已添加說明,但代碼編譯):
// http://msdn.microsoft.com/en-us/library/aa288459(VS.71).aspx
// delegates are a lot like function pointers and events "appear" to be a lot like delegates.
// in a sense, a delegate is a function pointer class. below is an example declaration
// of a delegate with an int return value, and two parameters (bool, string)
public delegate int MyDelegate(bool abool, string astring);
// delegates behind the scenes are actually of the System.MulticastDelegate type, and therefore
// can have multiple invocations.
// see http://msdn.microsoft.com/en-us/library/system.multicastdelegate.aspx
class DelegatesAndEvents
{
// delegates can also be defined inside classes
public delegate void AnotherDelegate();
// Delegates can be instantiated just like any variable or field
public AnotherDelegate DelegateInstance;
public DelegatesAndEvents()
{
// add method/delegate to the invocation list
DelegateInstance += Method;
// or another syntax
DelegateInstance += new AnotherDelegate(Method);
// remove a method/delegate to the invocation list
DelegateInstance -= Method;
// or the more formal syntax
DelegateInstance -= new AnotherDelegate(Method);
// set the invocation list to a single method/delegate
DelegateInstance = Method;
// or the more formal syntax
DelegateInstance = new AnotherDelegate(Method);
// to clear a delegate, assign it to null:
DelegateInstance = null;
// for all the previous operators, its very important to note
// that they instantiate a new MulticastDelegate in the process.
// this means that every add (+=) or remove(-=) generates a new
// MulticastDelegate. Look at the following scenario:
DelegateInstance = Method;
// invoking a will call Method
AnotherDelegate a = DelegateInstance;
DelegateInstance += AnotherMethod;
// now, invoking a will still only invoke Method, while
// invoking DelegateInstance will invoke both Method
// and AnotherMethod.
// NOTE NOT BEST PRACTICE SEE BELOW
a(); // invokes Method
DelegateInstance(); // invokes Method and AnotherMethod
// The main importance of this fact deals with thread safety
// when invoking delegates. When invoking a delegate, you
// should always do a null-check before invocation to avoid
// an exception:
// NOTE NOT BEST PRACTICE SEE BELOW
if (a != null)
{
a();
}
// the problem with the above code is that if another thread removes
// Method from a, after the null check, trying to invoke a will throw
// an exception. To get around this, since we stated before that the
// remove operation recreates the MulticastDelegate, assigning the
// delegate to a temporary delegate before doing the null check, and
// then invoking that temporary delegate should avoid threading problems
//**************************************************************
// NOTE THIS IS BEST PRACTICE FOR INVOKING A DELEGATE/EVENT
// This is thread-safe
AnotherDelegate aCopy = a;
if (aCopy != null)
{
aCopy();
}
//**************************************************************
}
// NOTE there is a way to avoid having to worry about null checking, with only
// a small overhead. assigning a delegate/event to an initial no-op function will
// simplify how it is invoked:
public AnotherDelegate ThirdDelegate = delegate { }; // this assigns a no-op delegate
// using this method, you'll be able to call the delegate without checking for
// null or use a temporary variable. this of course is only true if no code
// sets ThirdDelegate to null anywhere.
public void Method()
{
// Delegates can be instantiated just like any variable or field
MyDelegate x = AFunction; // shorthand way of creating a delegate from an actual function
x = new MyDelegate(AFunction); // the more formal way of creating a delegate
// if a delegate hasn't been assigned anything, trying to call it will throw an exception
// not really necessary here though since we just assigned it
if (x != null)
{
int somevalue = x(false, "10");
}
}
public void AnotherMethod()
{
// Do Nothing
}
public int AFunction(bool somebool, string somestring)
{
if (somebool)
{
return 1;
}
int avalue;
if (int.TryParse(somestring, out avalue))
{
return avalue;
}
return 0;
}
// EVENTS
// events are types as delegates but avoid a couple of issues with
// instantiating delegates as members of a class. unlike delegates
// events can only be created within a class or struct (ie not as
// a standalone type in a namespace). to create an event, add the
// event keyword:
public event AnotherDelegate AnotherEvent;
// the above is actually the shorthand way of instantiating an event
// the full way is below:
private MyDelegate someEvent;
public event MyDelegate SomeEvent
{
add
{
someEvent += value;
}
remove
{
someEvent -= value;
}
}
// EXPLANATION OF HOW AN EVENT DIFFERS FROM A DELEGATE
// events are actually similar to properties in that they wrap a
// non-public delegate. this prohibits an external source from
// doing two things that most likely aren't desired:
// external code can't invoke the delegate
// external code can't do: classInstance.SomeEvent(...parameters...);
// external code can't set the delegate
// external code can't do: classInstance.SomeEvent = somedelegate;
// this effectively makes an event something that occurs within class, and
// controlled by the class, but can be subscribed to by external code.
// events usually derive from the EventHandler or EventHandler<T> delegates
// which have the following definitions:
// void EventHandler(object sender, EventArgs e)
// void EventHandler<T>(object sender, T e)
// the common way to use these is to always send the class instance that
// raised the event, as well as some event arguments that contain more
// information about the event. see below for an example of extending
// EventArgs.
public event EventHandler<TakeOffEventArgs> TakeOff;
public void PerformTakeOff()
{
EventHandler<TakeOffEventArgs> takeOffTemp = TakeOff;
if (takeOffTemp != null)
{
takeOffTemp(this, new TakeOffEventArgs("Spaceship", double.MaxValue));
}
}
}
public class TakeOffEventArgs : EventArgs
{
public TakeOffEventArgs(string aircraft, double speed)
{
Aircraft = aircraft;
Speed = speed;
}
public string Aircraft { get; set; }
public double Speed { get; set; }
}
感謝所有樣品將就一下吧,看哪個答案是最適合我。 – user310291 2011-04-23 18:47:59
不清楚你將如何做什麼?這篇文章非常清楚地解釋了它,它只是將訂閱包裝在訪問器中。 – 2011-04-23 16:46:37
這是我不明白什麼是不明確的給你。你沒有解釋它。 – 2011-04-23 16:50:29
由於有些人已經回答了這些版主如何假裝問題是模糊的? – user310291 2011-05-22 20:46:57