C#におけるFuncとActionデリゲートの実用的活用

C#ではデリゲートを使用する際、通常は以下のようにデリゲート型を宣言します:

private delegate string GreetDelegate();

この例では、stringはデリゲートに適合するメソッドの戻り値型を示し、デリゲート名GreetDelegateにはパラメータがありません。

デリゲートに適合するメソッドを定義:

public static string GetGreetingMessage()
{
    return "こんにちは";
}

呼び出し例:

static void Main(string[] args)
{
    GreetDelegate greet = GetGreetingMessage;
    Console.WriteLine(greet());
}

デリゲート変数を事前に宣言せずに使用するには、Funcデリゲートを活用します。

Funcデリゲートの基本

Func<TResult>:パラメータなしでTResult型を返すデリゲート

static void Main(string[] args)
{
    Func<string> greet = GetGreetingMessage;
    Console.WriteLine(greet());
}

Func<T, TResult>:1つの入力パラメータを受け取るデリゲート

Func<string, int> parser = ConvertToInteger;

public int ConvertToInteger(string input)
{
    return int.Parse(input);
}

入力パラメータが増える場合は、Func<T1, T2, TResult>などのバリエーションを使用します。

匿名メソッドとの連携

public static void Main()
{
    Func<string, int, string[]> segmenter = delegate(string text, int limit)
    {
        char[] delims = { ' ', ',', '.' };
        return limit > 0 ? text.Split(delims, limit) : text.Split(delims);
    };

    string title = "こころ";
    foreach (string word in segmenter(title, 3))
        Console.WriteLine(word);
}

ラムダ式との連携

public static void Main()
{
    char[] separators = { ' ' };
    Func<string, int, string[]> segment = (s, i) => 
         i > 0 ? s.Split(separators, i) : s.Split(separators);

    foreach (string word in segment("羅生門", 2))
        Console.WriteLine(word);
}

Actionデリゲート

戻り値がない場合(voidメソッド)はActionを使用:

static void Main(string[] args)
{
    Action logger = WriteLog;
    logger();
}

public static void WriteLog()
{
    Console.WriteLine("ログを出力");
}

Action<T>:1つのパラメータを受け取るバージョン

static void Main(string[] args)
{
    Action<string> logger = WriteMessage;
    logger("処理完了");
}

public static void WriteMessage(string message)
{
    Console.WriteLine(message);
}

ラムダ式との組み合わせ

static void Main(string[] args)
{
    Action<string> simpleLogger = msg => Console.WriteLine(msg);
    simpleLogger("簡易ログ出力");
}

タグ: C# デリゲート Func Action ラムダ式

6月28日 22:05 投稿