Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

EventInfo.GetRaiseMethod() always null

I have:

event EventHandler MyEvent;

MyEvent += new EventHandler(someHandler);

if(this.GetEvent("MyEvent").GetRaiseMethod() == null)
{
  // Always true...
}

But why? After I add a handler, shouldn't GetRaiseMethod() be set to someHandler's MethodInfo?

like image 876
poy Avatar asked Feb 14 '13 22:02

poy


2 Answers

This is a quirk of C#, it doesn't support raise accessors. Only add and remove. Other .NET languages like VB.NET, F# and C++/CLI do support them and it is well defined in the CLI spec, named "fire" in that one.

It is hard to explain why the C# team skipped it, I've never seen a good explanation for it. Pure speculation: it may have had something to do with their desire to avoid the cost of constructing the event arguments for an event that nobody subscribed. Very common in the GUI frameworks. It is a bit of a loss, hundreds of thousands of hours must have been lost by C# programmers writing the standard raise event pattern as well as diagnosing NREs when they forgot to check for null. The elvis operator (?.) in C# v6 finally made it easier.

Anyhoo, you'll never get anything but null from GetRaiseMethod() if you reflect code written in C#. You'll however always get a non-null when it was written in VB.NET, F# or C++/CLI. You'll have to dig out the backing delegate variable if you need to raise the event with reflection, that can be painful. If the auto-generated add/remove accessors were used then the backing variable has the same name as the event and you can retrieve it with Type.GetField(), using BindingFlags.NonPublic | BindingFlags.Instance.

like image 165
Hans Passant Avatar answered Oct 19 '22 06:10

Hans Passant


The raise method is one of the accessors mentioned in the CLI specification in addition to "add" and "remove" - however, most events simply don't implement this feature. In particular, c# specifically does not support this - so yes: that will always return null.

like image 41
Marc Gravell Avatar answered Oct 19 '22 05:10

Marc Gravell