Delegate Variety in C#

Delegate Variety in C#

One of the constructs many junior programmers struggle with is the delegate. Coming from a world of Visual Basic or Java, many have never seen a function pointer (as a C programmer would every day), so the concept of referencing a function or method in a variable is completely foreign to them. In the early days of C#, delegates had to be instantiated with named methods and were somewhat cumbersome. Today, anonymous delegates and lambda expressions are profuse in many popular frameworks and APIs, so it's important to take a bit of time to cement these concepts into our brains. To help some VB6 programmers adapt to C# and the many equivalent flavors of delegates, I walked through some simple samples to show them the different flavors of delegates. Below is a complete sample showing a few different ways to declare delegates in C#.

using System; using System.Collections.Generic; using System.Linq;

namespace DelegateExample { class Program { public delegate string ProcessStringDelegate(string data);

    public static string ReverseStringStaticMethod(string data)
    {
        return new String(data.Reverse().ToArray());
    }

    static void Main(string\[\] args)
    {
        var stringDelegates = new List<ProcessStringDelegate>
        {
            //==========================================================
            // Declare a new delegate instance and pass the name of the method in
            new ProcessStringDelegate(ReverseStringStaticMethod),
            
            //==========================================================
            // A shortcut is to just and pass the name of the method in
            ReverseStringStaticMethod,
            
            //==========================================================
            // You can create an anonymous delegate also
            delegate (string inputString) //Scramble
            {
                var outString = inputString;
                if (!string.IsNullOrWhiteSpace(inputString))
                {
                    var rand = new Random();
                    var chs = inputString.ToCharArray();
                    for (int i = 0; i < inputString.Length \* 3; i++)
                    {
                        int x = rand.Next(chs.Length), y = rand.Next(chs.Length);
                        char c = chs\[x\];
                        chs\[x\] = chs\[y\];
                        chs\[y\] = c;
                    }
                    outString = new string(chs);
                }
                return outString;
            },

            //==========================================================
            // yet another syntax would be the lambda expression syntax
            inputString => { // ROT13
                var array = inputString.ToCharArray();
                for (int i = 0; i < array.Length; i++)
                {
                    int n = (int)array\[i\];
                    n += (n >= 'a' && n <= 'z') ? 
                        ((n > 'm') ? 13 : -13) : 
                            ((n >= 'A' && n <= 'Z') ? 
                            ((n > 'M') ? 13 : -13) : 0);

                    array\[i\] = (char)n;
                }
                return new string(array);
            }
            //==========================================================
        };

        // Display the results of the delegate calls
        var stringToTransform = "Welcome to the jungle!";

        System.Console.ForegroundColor = ConsoleColor.Cyan;
        System.Console.Write("String to Process: ");
        System.Console.ForegroundColor = ConsoleColor.Yellow;
        System.Console.WriteLine(stringToTransform);

        stringDelegates.ForEach(delegatePointer =>
        {
            System.Console.WriteLine(); 

            System.Console.ForegroundColor = ConsoleColor.Cyan;
            System.Console.Write("Delegate Method Name: ");
            System.Console.ForegroundColor = ConsoleColor.Magenta;
            System.Console.WriteLine(delegatePointer.Method.Name);

            System.Console.ForegroundColor = ConsoleColor.Cyan;
            System.Console.Write("Delegate Result: ");
            System.Console.ForegroundColor = ConsoleColor.White;
            System.Console.WriteLine(delegatePointer(stringToTransform));
        });

        System.Console.ReadKey();
    }
}

}

The output of the program is below:

String to Process: Welcome to the jungle!

Delegate Method Name: ReverseStringStaticMethod Delegate Result: !elgnuj eht ot emocleW

Delegate Method Name: ReverseStringStaticMethod Delegate Result: !elgnuj eht ot emocleW

Delegate Method Name:

b__1 Delegate Result: cg ljotWotem!le une eh

Delegate Method Name:

b__2 Delegate Result: dX_V|`X ?| ?[X ]?{Z_X!

This article is part of the GWB Archives. Original Author: Justin Greenwood

New on Geeks with Blogs

  • We Won The One Award I Actually Care About

    Full Scale made the Inc. 5000 for the fifth year straight, the 12th listing across my three companies. Here is why the one award you cannot buy is worth stopping for.

  • Your Customers Build the Features Now

    I let a tool I liked sit dead for a year rather than build the features I wanted. An MCP server meant I never had to, and your customers can do the same to your product.

  • Get the Size of a Directory in Linux the Easy Way

    du -sh for the quick answer, ncdu for the cleanup, df for the disk itself: every command for checking directory size in Linux, plus why du and df never agree.

  • Vim Search and Replace: The Ultimate Guide

    One :%s command replaces every match in a file before a find dialog would even open. The Vim substitute patterns worth the muscle memory: flags, ranges, capture groups, and multi-file edits.