In one of my older blogs I have written a short tutorial on delegates and events.
I wrote the blog after reviewing the concepts of delegates and events and wanted to create a hopefully simplified version of the material for my blog readers.
Recently I have come across another C# class that is a wrapper on a delegate that does not return any values. This class is called Action and one can read more about it on the MSDN site.
Action class simplifies creation of delegates that do not need to return a value. Several built-in features of C# use Action class. One of these is Parallel.ForEach() which can be used to loop through an enumerable collection in a parallel fashion. A call to ForEach would accepts two arguments: the IEnumerable collection and Action delegate (perhaps anonymous) to perform on each item in the collection. Here is a quick example code that prints out the content of intList in asynchronous manner:
List<int> intList = new List<int>() {1,2,3,4,5}; Parallel.ForEach(intList, (e, state, i) => Console.WriteLine(e.ToString()));
If you examine the IL code for the above, you will see that an instance of System.Action class encapsulates the anonymous method.
Thinking about the Action class got me thinking if I could rewrite my previous delegate tutorial with a simplified syntax. This is what I have come up with:
using System; using System.Threading.Tasks; using System.Collections; namespace ActionsAndEvents { public class ListWithEightEvent : ArrayList { // event on an action public event Action EnteredEight; // invoke event after an addition of an 8 public override int Add(object value) { int i = base.Add(value); if (EnteredEight != null && value.ToString() == "8") EnteredEight(); return i; } } class Test { public static void Main() { ListWithEightEvent list = new ListWithEightEvent(); // register the event with AddedEight method list.EnteredEight += AddedEight; string input; Console.WriteLine("Keep entering numbers. Enter 'x' to stop."); do { input = Console.ReadLine(); list.Add(input); } while (input != "x"); } // This will be called whenever the list receives an 8 public static void AddedEight() { Console.WriteLine("You have entered an 8!"); } } }
To me, the above code is cleaner and simpler than the earlier delegate and EventHandler version.