In this post we will learn about “Delegate in C#”. A delegate is a person who represents an organization or group of people. In the C# world, a delegate is a reference type variable that represents one or a set of methods while retaining their reference. These References can also be changed at runtime. So, let’s start by understanding what does this means.
Let’s create a class named BasicMaths that has two methods Add() and Subtract(), which perform addition and subtraction respectively.
public class BasicMaths
{
public static double Add (double value1, double value2)
{
return value1 + value2;
}
public static double Subtract (double value1, double value2)
{
return value1 - value2;
}
}
The first point to remember is that a delegate is type safe, which means it can only contain method references that have the same number of parameters, type and return type, meaning in our case both methods. formula has two parameters, both type double and return type are same i.e., Double, so it must be referenced by a delegate of the same frame, let’s declare our delegate.
public delegate double MathDelegate (double value1, double value2);
Note: it looks similar to the methods Add() and Subtract(), let’s have a closer look.
Now let’s focus on how to invoke the delegate. In order to invoke this first we need to first create an instance of the delegate and register method to it; it can be at the time of instantiating the delegate as shown below:
public class MathTest
{
public delegate double MathDelegate (double value1, double value2);
public static void Main()
{
MathDelegate mathDelegate = new MathDelegate(BasicMaths.Add);
var result = mathDelegate(5, 2);
Console.WriteLine(result);
// output: 7
MathDelegate anotherMathDelegate = new MathDelegate(BasicMaths.Subtract);
result = anotherMathDelegate(5, 2);
Console.WriteLine(result);
// output: 3
}
}
Multicasting of a Delegate
We can create a calling list of methods that can be called when a delegate is called, this is called multicasting to a delegate. To do this, we need to be aware of the role of the + and – operators. The + operator helps add elements (method references) to the calling delegate list while the minus operator helps remove elements from the calling list.
Let’s check below example:
public class Test
{
public delegate double MathDelegate (double value1, double value2);
public static void Main()
{
MathDelegate mathDelegate = new MathDelegate(BasicMaths.Add);
mathDelegate += BasicMaths.Subtract;
// now when mathDelegate is invoked it calls both the method BasicMaths.Add and BasicMaths. Subtract.
// if we wants BasicMaths.Add to be removed from invocation list we can do
// mathDelegate -= BasicMaths. Add
// so that next time when the delegate is invoke it only calls BasicMaths.Subtract
}
}
Note:
- The sequence in which the methods are called are same in which they were added in the invocation list.
- It’s not necessary that delegates only hold a reference to static methods.
Must Read: Quickly convert for-to-foreach
Usage of Delegates
Let’s check real time usage of delegates.
Let’s say we want a situation where the user wants to print an item in multiple places for simplicity, assuming the result is printed to the console application as well as a flat file.
This can be done any time you want to print calling methods to the console as well as writing to an individual flat file, or you can create a delegate that contains references to those methods and just call the delegate when you want. print, we will do it the second way using delegate.
public class ConsolePrinting
{
public void WriteToConsole(int number)
{
Console.WriteLine("The number is - {0}", number);
}
}
public class FilePrinting
{
public void PrintIntoFile(int number)
{
using (var fileStream = new FileStream(@"c:\demo\file.txt", FileMode.Append, FileAccess.Write))
{
using (var streamWriter = new StreamWriter(fileStream))
{
streamWriter.WriteLine("The number is - {0}", number);
}
}
}
}
public class MulticastDeletage
{
public delegate void Printing(int number);
public static void Main()
{
var filePrinting = new FilePrinting();
var consolePrinting = new ConsolePrinting();
var printing = new Printing(filePrinting.PrintIntoFile);
printing += consolePrinting.WriteToConsole;
for (int i = 1; i < 11; i++)
{
if (i % 2 == 0)
{
printing(i);
}
}
}
}
You can check more article on our website under C# section HERE or you can also check more such stuff on Microsoft Docs too.