多播代理必须具有返回类型void。为什么?

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了多播代理必须具有返回类型void。为什么?相关的知识,希望对你有一定的参考价值。

多播代理必须具有返回类型void否则将引发异常。

我想知道它背后的原因是什么,如果多个方法可以具有与委托相同的返回类型呢?

答案

前提是错误的;它工作正常:

Func<int> func = delegate { Console.WriteLine("first part"); return 5; };
func += delegate { Console.WriteLine("second part"); return 7; };
int result = func();

这是一个带有非void结果的多播委托,工作正常。您可以从控制台看到两个部分都已执行。最后一项的结果是返回的结果。我们可以证明这是一个真正的多播委托:

if(func is MulticastDelegate) Console.WriteLine("I'm multicast");

即使只在第一行(当只列出一种方法时),它也会写“我是多播”。

如果您需要更多地控制单个结果,请使用GetInvocationList()

foreach (Func<int> part in func.GetInvocationList())
{
    int result = part();
}

它允许您查看每个单独的结果。

在IL术语中:

.class public auto ansi sealed Func<+ TResult>
    extends System.MulticastDelegate`

也就是说:Func<T>继承自MulticastDelegate。基本上,对于所有意图和目的,.NET中的所有代理都是多播委托。您可能能够在托管C ++中获得非多播委托,我不知道。但肯定不是来自C#。

另一答案

以下答案实际上是错误的,因为您目前*可以*具有非void返回类型的多播委托(陪审团仍然没有考虑这是否一直如此)。但是,它确实回答了“为什么一种语言不允许这样的代表?”的问题,所以我将其留作完整性。

现在去投票马克。


因为多个方法会返回多个值,那么委托的一个返回值应该是什么呢?显然,在任何情况下都没有令人满意的答案。您可以争辩多播委托应该:

  • 返回调用顺序中第一个方法的值(但是未指定IIRC调用顺序,那么这将如何工作?)
  • 返回上一个方法的值,如上所述
  • 返回所有代理返回的单个不同值;如果并非所有人都同意,则抛出异常
另一答案

在多播中,问题是它覆盖所有值只是打印最后一个方法值,如果它有返回类型,所以你必须逐个捕获返回类型,让我们看看下面的代码

 class Program
{
    // i am going to add and subtract two num but i wanna get result in string the same thing you can do for int and what ever you want
      delegate string mydeledagte(int a,int b);
      delegate string d(int s, int t);
    static void Main(string[] args)
    {
        mydeledagte ab = new mydeledagte(ad);
        mydeledagte d= new mydeledagte(sub);
        mydeledagte multi = ab + d;

        foreach (mydeledagte individualMI in multi.GetInvocationList())
        {
            string retVal = individualMI(3, 5);
            Console.WriteLine("Output: " + retVal);
            Console.WriteLine("
***developer of KUST***");
            Console.ReadKey();
        }
    }
    static string ad(int a, int b)
    {

        return (a + b).ToString();

    }
    static string sub(int a, int b)
    {

        return (a - b).ToString(); ;
    }
}

以上是关于多播代理必须具有返回类型void。为什么?的主要内容,如果未能解决你的问题,请参考以下文章

委托泛型委托多播委托匿名函数lamda表达式事件

为啥我无法在具有 void 返回类型的异步函数中捕获异常?

具有 void 返回类型的 switch 表达式

未使用 PYQT5 多播 UDP 接收数据报

具有 UNNotificationRequest 的计算属性返回无法将类型“Void”的返回表达式转换为返回类型“[UNNotificationRequest]”

递归 - 具有 void 函数返回类型的反向 LinkedList