Делегирование шаблона и ключевое слово delegate в С#

Из документа MSDN:

Делегат - это тип, который безопасно инкапсулирует метод, аналогичный указатель функции в C и С++. В отличие от указателей функций C, делегаты являются объектно-ориентированными, безопасными по типу и безопасными.

Я знаю, что это такое и как его использовать. Но мне интересно, написана ли база на шаблоне делегата, который я знаю (от wikipedia).
В чем разница между ними?

Ответ 1

Делитель С# (не шаблон) может быть полезен, когда вы реализуете шаблон делегирования просто посмотрите на эту реализацию шаблона делегата из википедии с помощью мои изменения:

//NOTE: this is just a sample, not a suggestion to do it in such way

public interface I
{
    void F();
    void G();
}

public static class A
{
    public static void F() { System.Console.WriteLine("A: doing F()"); }
    public static void G() { System.Console.WriteLine("A: doing G()"); }
}

public static class B
{
    public static void F() { System.Console.WriteLine("B: doing F()"); }
    public static void G() { System.Console.WriteLine("B: doing G()"); }
}

public class C : I
{
    // delegation 
    Action iF = A.F;
    Action iG = A.G;

    public void F() { iF(); }
    public void G() { iG(); }

    // normal attributes
    public void ToA() { iF = A.F; iG = A.G; }
    public void ToB() { iF = B.F; iG = B.G; }
}

public class Program
{
    public static void Main()
    {
        C c = new C();
        c.F();     // output: A: doing F()
        c.G();     // output: A: doing G()
        c.ToB();
        c.F();     // output: B: doing F()
        c.G();     // output: B: doing G()
    }
}

Опять делегат может быть полезен здесь, но это не значит, что он был введен. Вы должны смотреть на него как на низкоуровневую конструкцию, а не на шаблон. В паре с событиями она может использоваться для реализации издателя/подписчика ( observer) - просто посмотрите в этой статье, или это может иногда помочь вам реализовать шаблон посетителя - это активно используется в LINQ:

public void Linq1() 
{ 
    int[] numbers = { 5, 4, 1, 3, 9, 8, 6, 7, 2, 0 }; 

    // n => n < 5 is lambda function, creates a delegate here
    var lowNums = numbers.Where(n => n < 5); 

    Console.WriteLine("Numbers < 5:"); 
    foreach (var x in lowNums) 
    { 
        Console.WriteLine(x); 
    } 
} 

Подводя итог: делегат языка не является самим шаблоном, он просто позволяет вам выполнять функции как объекты первого класса.

Ответ 2

шаблон делегирования:

шаблон дизайна [...], где объект вместо выполнения одной из своих заявленных задач делегирует эту задачу связанному вспомогательному объекту.

К сожалению, эта страница не описывает много о том, когда ее использовать или какие шаблоны вытекают из нее, кроме

Шаблон делегирования является одним из основных шаблонов абстракции, лежащих в основе других программных паттернов, таких как композиция (также называемая агрегацией), mixins и аспекты.

На странице, которая описывает делегирование, вы можете понять, что она должна делегировать реализацию функции классу, который может или не может быть известными во время выполнения. Когда вы говорите Foo.Bar(), реализация этого может делегировать выполнение Bar() предшествовавшему "вспомогательному объекту".

Теперь для делегата С#, как указано, это просто указатель на функцию. Он может помочь реализовать шаблон делегирования, назначив метод делегирования либо во время компиляции, либо во время выполнения.

Ответ 3

Шаблон делегирования - это способ для объекта делегировать ответственность за задачу внешнему методу. Он использует делегат для отслеживания этого метода. Поэтому для делегата нужно использовать шаблон делегирования.

Этот шаблон используется, например, в методе List<T>.Sort(comparison), где алгоритм сортировки использует делегат, который вы предоставляете ему для сравнения элементов.