调用和DynamicInvoke之间的区别
委托中的Invoke和DynamicInvoke有什么区别?请给我一些代码示例,说明这两种方法之间的区别。
回答:
当您有一个委托实例时,您可能知道确切的类型,或者可能只是知道它是一个Delegate
。如果您知道确切的类型,则可以使用Invoke
,它
-一切都已预先验证。例如:
Func<int,int> twice = x => x * 2;int i = 3;
int j = twice.Invoke(i);
// or just:
int j = twice(i);
然而!如果您只是知道它是Delegate
,它必须手动解析参数等-这可能涉及拆箱等-正在进行很多反射。例如:
Delegate slowTwice = twice; // this is still the same delegate instanceobject[] args = { i };
object result = slowTwice.DynamicInvoke(args);
请注意,我已经写了args
很长的篇幅以明确指出object[]
涉及到了。这里有很多额外费用:
- 数组
- 验证传递的参数是否适合实际
MethodInfo
- 拆箱等必要
- 反射调用
- 那么调用者需要做一些事情来处理返回值
基本上,尽可能避免DynamicInvoke
。Invoke
总是可取的,除非您所拥有的都是a Delegate
和an object[]
。
为了进行性能比较,在调试器(控制台exe)之外的释放模式下打印以下内容:
Invoke: 19msDynamicInvoke: 3813ms
码:
Func<int,int> twice = x => x * 2;const int LOOP = 5000000; // 5M
var watch = Stopwatch.StartNew();
for (int i = 0; i < LOOP; i++)
{
twice.Invoke(3);
}
watch.Stop();
Console.WriteLine("Invoke: {0}ms", watch.ElapsedMilliseconds);
watch = Stopwatch.StartNew();
for (int i = 0; i < LOOP; i++)
{
twice.DynamicInvoke(3);
}
watch.Stop();
Console.WriteLine("DynamicInvoke: {0}ms", watch.ElapsedMilliseconds);
以上是 调用和DynamicInvoke之间的区别 的全部内容, 来源链接: utcz.com/qa/400942.html