C# asynchronous events

meteoraln
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by meteoraln »

I have an event with a lot of listeners on it. I just found out that doing eventblah(y, z) calls each of the listeners synchronously. I want to call them all at the same time async.



Saw something on the internet for eventblah.GetInvocationList(), and then iterating and calling the BeginInvoke() for each delegate. I want to avoid calling EndInvoke.



Half the articles on the net says I need to call EndInvoke or else I'll have a resource leak. The other half of the articles say it's ok to not call EndInvoke. I suspect maybe the older .NET versions required you to call EndInvoke? I've been watching my process in task manager and it doesn't look like memory usage is increasing when I do this.



Anyone know the proper / best way to do this?
User avatar
FDAXHunter
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by FDAXHunter »

Hum... I think this is one of those things: You're supposed to call EndInvoke, and everyone in their right programming mind will tell you that it is required... or potentially nothing is guaranteed. It's not considered optional, but there may be certain times where your own implementations (i.e. your own methods that are firing) may get away with not having EndInvoke(). And this is probably what you are observing?



On memory leaks: you may not notice a memory leak, but that doesn't mean that in some other version, or potentially even some other OS/hardware configuration, there won't be. Because, you know... the standard rules of engagement assume that you will be calling EndInvoke().



Long story short... call EndInvoke (which is not what you want to hear, but that's usually the case for all best practices). I don't think you'll find a serious developer that will light-heartedly tell you that you can avoid it.
The Figs Protocol.
meteoraln
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by meteoraln »

Being a programmer, I guess I'm naturally lazy. I'd like to pass a templated callback function and handle EndInvoke inside the callback. This way, I could write it just once. Would this be an acceptable design?
User avatar
FDAXHunter
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by FDAXHunter »

I think you have good reason to be lazy. "Fire-and-forget" implementations are desirable features, especially nowadays with many applications having access to an oversupply of processing cores. It's unfortunate that apart from thread pool, and Task and async and what not there isn't something more light-weight.



I'm not sure what a "templated callback" would look like?
The Figs Protocol.
meteoraln
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by meteoraln »

http://stackoverflow.com/questions/11392978/c-sharp-calling-endinvoke-in-callback-using-generics



something along the lines of this, which would let me write one callback for everything.
User avatar
FDAXHunter
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by FDAXHunter »

Gotcha. That's a nice, compact solution, although less than clear for debugging purposes/codetracing purposes.



But then again, neither is async or any of the other crutches, once you look at how bloated the state machine that gets generated under the covers actually is. Ultimately, it all depends on how it's used. But in principle, I think that's not a bad way to go.
The Figs Protocol.
weismat2
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by weismat2 »

Which kind of application are you talking about?

Is the BeginInvoke used to update GUI elements and are you sure that the subscribers to the events are thread-safe?

If you are in a pure server-scenario a Parallel.Foreach on the invocation list would be a lot easier.

Another word of warning is that this parallelization adds overhead (smaller than threads with tasks) - so when you do not know your subscribers well, it might not really improve things.
meteoraln
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by meteoraln »

This will not be for GUI, and I don't need thread safety. I had a look at Parallel.Foreach. It's exactly what I need. It even stops of further code until all items in collection are processed!!
User avatar
athletico
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by athletico »

Parallel.ForEach and TPL is very nice, especially for relatively graceful exception handling.



I'm looking at Reactive Extensions for the same kind of problem, launching async tasks in server code.  The design of IObservable and IObserver has a mathematical purity to it; these interfaces nicely complement IEnumerable (one is push, the other pull).  I'd be curious to hear from those who have fearlessly gone down the Rx path and have any gotchas to share.
IVolrev
Posts: 0
Joined: Thu Jan 01, 2004 12:00 am

C# asynchronous events

Post by IVolrev »

@Athletico,



I have not used Rx, but I extensively use the TPL Dataflow library and find the latency and throughput very impressive. There are still things to be desired but its a relatively new addition to the .Net framework. So far, it shows a lot of promise.



@meteoraln, I actually recommend you to take a look at whether TPL Dataflow could solve your problem. I ran several tests and compared APIs I wrote, implementing an event call back structure vs. a dataflow structure in which data blocks are linked to each other and the tpl df won hands down in terms of throughput and latency. The particular tests I ran was for a project feeding tick based data into a profiling and testing engine container. I managed to feed tick data from a custom binary data store into the testing container at a rate of about 10 million ticks per second without a single custom delegate and event.
Post Reply