簡體   English   中英

如何在 C# 中的操作中添加另一個操作?

[英]How to add another action to an action in C#?

為什么這段代碼只打印“A”和“B”,而不打印“C”?

Action act = null;
act += () => MessageLog.Message("A");
act += () => MessageLog.Message("B");
Action<Action> add = a => a += () => MessageLog.Message("C");
add(act);
act.Invoke();

代表是不可變的。 +=運算符創建一個委托,其調用列表由左側的調用列表和運算符右側的調用列表組成。 然后它將對該委托的引用存儲在左側的變量中。 所以

act += () => MessageLog.Message("A");

相當於

act = act + (Action) (() => MessageLog.Message("A"));

這又相當於:

act = (Action) Delegate.Combine(act, (Action) (() => MessageLog.Message("A"));

所以,現在我們可以來找你的add代表了。 這個 lambda 表達式:

a => a += () => MessageLog.Message("C");

...修改參數a以引用新組合的委托...然后忽略它。

相反,您需要返回組合委托(因此將add更改為Func<Action, Action> ),然后在調用add時使用返回值:

Action act = null;
act += () => MessageLog.Message("A");
act += () => MessageLog.Message("B");
Func<Action, Action> add = a => a + () => MessageLog.Message("C");
act = add(act);
act.Invoke();

您可能知道, A += B只是A = A + B簡寫,因此您的add委托實際上只是:

a => a = a + () => MessageLog.Message("C")

+創建組合委托a + () => MessageLog.Message("C") ,然后=將其分配回a 請注意您是如何重新分配參數a ,現在應該清楚的是,這根本不會更改傳入 ( act ) 的變量

除了返回組合委托之外,您還可以通過引用傳遞act

delegate void ByRefAction<T>(ref T parameter);

...

    Action act = null;
    act += () => Console.WriteLine("A");
    act += () => Console.WriteLine("B");
    ByRefAction<Action> add = (ref Action a) => a += () => Console.WriteLine("C");
    add(ref act);
    act.Invoke();

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM