【问题标题】:Why there must be a delegate to bridge a Thread and its Method?为什么必须有一个委托来桥接线程及其方法?
【发布时间】:2012-04-19 14:41:17
【问题描述】:

常见的代码如下:

Work w = new Work();
w.Data = 42;
threadDelegate = new ThreadStart(w.DoMoreWork);
newThread = new Thread(threadDelegate);
newThread.Start();

我只是想知道,为什么必须有一个委托来桥接线程和在该线程上执行的方法?

我们可以直接将方法名称发送到线程吗?

【问题讨论】:

    标签: .net multithreading delegates


    【解决方案1】:

    我们可以直接将方法名称发送到线程吗?

    作为字符串?万维网。如果不是作为字符串,您将如何建议告诉线程要执行什么?委托是在 .NET 中表示“使用特定签名执行的东西”的惯用方式。

    请注意,您不需要使用new ThreadStart 或使用单独的变量。使用方法组转换可以正常工作:

    newThread = new Thread(w.DoMoreWork);
    newThread.Start();
    

    或者,如果您不需要所有这些变量:

    new Thread(new Work { Data = 42 }.DoWork).Start();
    

    编辑:请注意,从 .NET 4 开始,通常最好将Task Parallel Library 用于此类事情。

    【讨论】:

    • @SteveTownsend:确实。如果可以的话,会将其添加到答案中,因为这是个好主意:)
    • 顺便说一句,Jon,托管委托和 C 函数指针之间是否存在类似用法(例如启动线程)之外的任何关系?我知道委托很可能拥有一个内部方法列表,因为它有 += 运算符,但是这里还能说什么呢?
    【解决方案2】:

    委托代表一种数据类型,就像 Integer 或 Double 代表它们各自的数据类型一样。委托定义了由其签名(返回类型和参数)标识的一类函数。就像 Integer 方法参数指定期望的 Integer 值一样,委托指定期望具有特定签名的方法。您需要指定预期的函数类型,原因与使用原始数据类型的原因相同。当你传入你的函数时,它传递了一个指向你想要调用的函数或对象方法的指针,即在内存中定义该函数的位置。如果您只是将函数名称作为字符串传入,它将不知道该名称的函数在哪里;除非您以某种方式定义了包含您要调用的函数的定义的类。

    有关代表的更多信息,请参阅以下内容:

    Info on C# delegates from Microsoft

    stackoverflow question - why-do-we-need-c-sharp-delegates

    以下链接是在 Java 中使用反射按名称调用方法的示例。如您所见,您需要指定哪个类包含您要调用的方法。委托的实际参数是直接指向方法的指针,这就是签名必须匹配的原因。

    Java reflection

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2012-04-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-09-13
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多