Friday, June 8, 2012

Multicast delegates in C#

In this post Multicast delegates in C# we shall see how to use delegates, to refer to more than method at the same time, to know more about the basics of Delegates refer to the post Delegates in C#.

Multicast delegates can hold the reference of more than one function at the same time; the calls to the functions are made in the order in which they are added to the delegate. The basic rule still remains the same; all methods referred by the delegate should have the same signature as the delegate.

When it comes to Multicast delegates there is an additional rule, the methods referred by Multicast delegates should have a return type of void, this is pretty straight forward, since the delegate is referring to multiple methods at the same time, it cannot keep track of the return values of all the methods.

References to multiple functions are added/removed using the += / -= operators respectively.

To add a reference use
myDelegate += new delMath(Add);

To remove a reference us
myDelegate -= new delMath(Add);

Let us understand Multicast delegates using a simple Calculator example, assume that our simple calculator supports 4 operations using the below 4 methods. This example is similar to the Delegates example which we saw in the post Delegates in C#, the difference is that here we use a ListBox instead of a DropDown, so that the user can select multiple operations at the same time.

private
void Add(int nNumber1, int nNumber2)
{
    strResult += "Add => " + (nNumber1 + nNumber2).ToString() + "";
}
//
private void Subract(int nNumber1, int nNumber2)
{
    strResult += "Subract =>" + (nNumber1 - nNumber2).ToString() + "";
}
//
private void Multiply(int nNumber1, int nNumber2)
{
    strResult += "Multiple => " + (nNumber1 * nNumber2).ToString() + "";
}
//
private void Divide(int nNumber1, int nNumber2)
{
    strResult += "Divide => " + (nNumber1 / nNumber2).ToString() + "";
}

Let us design a simple .aspx page as follows.



The user can enter 2 numbers in the Textboxes, select the multiple operations in the Listbox and click on the Evaluate button to perform the calculation.

Now let us declare a delegate to call the appropriate functions of all the options selected by the user. The signature of the delegate should match the signature of the methods with which it will be associated, here the 4 methods take 2 integers as parameters and return a void, hence we will declare a delegate with the same signature.

public delegate void delMath(int nNumber1, int nNumber2);

In the Click event of the Evaluate button, we shall initialize the Delegate and make it point to the appropriate method, based on the option selected by the user.
//
protected void cmdEvaluate_Click(object sender, EventArgs e)
{
    delMath myDelegate = null;       
    for (int i = 0; i < lstOperation.Items.Count; i++)
    {
      if (lstOperation.Items[i].Selected == true)
       {
            switch (lstOperation.Items[i].Value)
            {
                case "Add":
                    {
                        myDelegate += new delMath(Add);
                        break;
                    }
                case "Subract":
                    {
                        myDelegate += new delMath(Subract);
                        break;
                    }
                case "Multiply":
                    {
                        myDelegate += new delMath(Multiply);
                        break;
                    }
                case "Divide":
                    {
                        myDelegate += new delMath(Divide);
                        break;
                    }
            }
        }
    }
    //
    myDelegate(Convert.ToInt16(txtNumber1.Text), Convert.ToInt16(txtNumber2.Text));
    lblResult.Text = strResult;
}
Finally we are just calling the delegate and passing the values entered by the user, note that we are not calling the method directly, the delegate will in turn call the referenced method and handle the return values.


The complete code for the example is as follows

.aspx page
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title>Delegates</title>
</head>
<
body>
<form id="frmDelegates" runat="server">
Enter Number1 <asp:TextBox
ID="txtNumber1"
runat="server">
</asp:TextBox> <br />

Enter Number2 <asp:TextBox
ID="txtNumber2"
runat="server">
</asp:TextBox> <br />

Select Operation

<asp: ListBox
ID="drpOperation"
runat="server">
SelectionMode="Multiple"
            <asp:ListItem
Value="Add"
Text="Add">
</asp:ListItem>
            <asp:ListItem
Value="Subract"
Text="Subract">
</asp:ListItem>
            <asp:ListItem
Value="Multiply"
Text="Multiply">
</asp:ListItem>
            <asp:ListItem
Value="Divide"
Text="Divide">
</asp:ListItem>
</asp: ListBox >

<asp:Button
ID="cmdEvaluate"
runat="server"
Text="Evaluate"
      onclick="cmdEvaluate_Click" />
<br /><br />

Result Expression:
<asp:Label ID="lblResult" runat="server"></asp:Label>
</form>
</body>
</
html>

.aspx.cs file
public partial class MulticastDelegates : System.Web.UI.Page
{
    public delegate void delMath(int nNumber1, int nNumber2);
    string strResult = "";
    //
    protected void cmdEvaluate_Click(object sender, EventArgs e)
    {
        delMath myDelegate = null;       
        for (int i = 0; i < lstOperation.Items.Count; i++)
        {
          if (lstOperation.Items[i].Selected == true)
           {
                switch (lstOperation.Items[i].Value)
                {
                    case "Add":
                        {
                            myDelegate += new delMath(Add);
                            break;
                        }
                    case "Subract":
                        {
                            myDelegate += new delMath(Subract);
                            break;
                        }
                    case "Multiply":
                        {
                            myDelegate += new delMath(Multiply);
                            break;
                        }
                    case "Divide":
                        {
                            myDelegate += new delMath(Divide);
                            break;
                        }
                }
            }
        }
    //
    myDelegate(Convert.ToInt16(txtNumber1.Text), Convert.ToInt16(txtNumber2.Text));
    lblResult.Text = strResult;
    }
    //
    private void Add(int nNumber1, int nNumber2)
    {
        strResult += "Add => " + (nNumber1 + nNumber2).ToString() + "";
    }
    //
    private void Subract(int nNumber1, int nNumber2)
    {
        strResult += "Subract =>" + (nNumber1 - nNumber2).ToString() + "";
    }
    //
    private void Multiply(int nNumber1, int nNumber2)
    {
        strResult += "Multiple => " + (nNumber1 * nNumber2).ToString() + "";
    }
    //
    private void Divide(int nNumber1, int nNumber2)
    {
        strResult += "Divide => " + (nNumber1 / nNumber2).ToString() + "";
    }
    //
    protected void Page_Load(object sender, EventArgs e)
    {

    }
}
}

That’s if we have seen how to use a Multicast delegate to call more than one method simultaneously.


Search Flipkart Products:
Flipkart.com

No comments: