Delegate ใน C# คือ Type-safe Function Pointer - ตัวแปรที่เก็บการอ้างอิงไปยังเมธอด สามารถส่งเมธอดเป็นพารามิเตอร์ เก็บในตัวแปร เรียกใช้ในภายหลังได้ เป็นพื้นฐานของ Events, Callbacks, LINQ, Async Programming
การประกาศ Delegate
// Syntax: delegate( ); public delegate void PrintString(string s); public delegate int Calculate(int a, int b); public delegate TResult Func<T, TResult>(T arg); // Built-in Generic Delegate
ตัวอย่างครบถ้วน: ใช้ Delegate สำหรับ Callback
using System;
using System.IO;
namespace DelegateAppl
{
class PrintString
{
static FileStream fs;
static StreamWriter sw;
// Delegate Declaration
public delegate void PrintStringDelegate(string s);
// Method 1: Print to Console
public static void WriteToScreen(string str)
{
Console.WriteLine("The String is: {0}", str);
}
// Method 2: Print to File
public static void WriteToFile(string s)
{
fs = new FileStream("message.txt", FileMode.Append, FileAccess.Write);
sw = new StreamWriter(fs);
sw.WriteLine(s);
sw.Flush();
sw.Close();
fs.Close();
}
// Method ที่รับ Delegate เป็น Parameter (Callback Pattern)
public static void SendString(PrintStringDelegate ps)
{
ps("Hello World");
}
static void Main(string[] args)
{
// สร้าง Delegate Instances
PrintStringDelegate ps1 = new PrintStringDelegate(WriteToScreen);
PrintStringDelegate ps2 = new PrintStringDelegate(WriteToFile);
// เรียกใช้ผ่าน Delegate
SendString(ps1); // Print to Screen
SendString(ps2); // Print to File
// Multicast Delegate
PrintStringDelegate multi = ps1 + ps2;
multi("Multicast!"); // เรียกทั้งสอง
Console.ReadKey();
}
}
}
ผลลัพธ์
The String is: Hello World
Built-in Generic Delegates (ใช้บ่อย)
Action- ไม่มี Return (void)Action<T1, T2...>- มี Parameter, ไม่มี ReturnFunc<TResult>- ไม่มี Parameter, มี ReturnFunc<T, TResult>- มี Parameter และ ReturnPredicate<T>- Func<T, bool> ใช้สำหรับ Filter
Multicast Delegates
Delegate สามารถชAIN หลายเมธอดได้: d += Method2; d -= Method1; เรียก d() จะรันทุกเมธอดในลำดับ
Delegate vs Lambda vs Anonymous Method
// Named Method
Action a1 = WriteToScreen;
// Anonymous Method (C# 2.0)
Action a2 = delegate(string s) { Console.WriteLine(s); };
// Lambda Expression (C# 3.0+) - แนะนำ
Action<string> a3 = s => Console.WriteLine(s);
Func<int, int, int> add = (x, y) => x + y;