19

我试图将在同一台机器上跨 AppDomain 进行通信的性能损失降到最低。在我的玩具示例中,A 类加载到 AppDomain 1 中。它创建一个 AppDomain 2 并在那里加载一个类 2 的实例(类 2 继承自 MarshalByRef)以获取代理。然后类 1 重复调用代理上的一个不返回值的方法。

我得到以下结果:

  1. 没有 AppDomain,两个类都加载在同一个 AppDomain 中,第一个类重复调用第二个方法(该方法没有参数):2400 万次方法调用/秒
  2. 如上所述的两个 AppDomain,方法没有参数或“出血”字符串参数:340.000 个方法调用/秒
  3. 如上所述的两个 AppDomain,一个可序列化参数(两个字符串的数组):64.000 次方法调用/秒

虽然我了解 2 和 3 (序列化)之间的性能损失,但我真的不明白为什么我从 case 1 到 case 2 慢了 100 倍。据我了解,一旦创建了代理,所有后续方法调用都必须非常快,因为没有数据从一个 AppDomain 编组到另一个。有人现在为什么跨 AppDomains 的通信如此缓慢?难道我做错了什么?

PS1。我对此的唯一提示是 “跨越 AppDomain 边界的成本令人尴尬。”。我猜他指的是序列化......

PS2。我不计算 AppDomain 或代理创建时间(我的基准测试从第一个方法调用开始)

PS3。我在 WinXP SP3 机器上使用 .NET 3.5。我还尝试了没有显着差异的 .NET 4.0 Beta 1。

4

3 回答 3

12

如果您计算每个场景中涉及的 IL 行数,您会发现 CLR 在远程处理时所做的工作量要高出 100 倍以上。直接调用只是几个操作码,但远程处理涉及多个类,真实/透明代理,安全检查,序列化,yadda yadda yadda。您需要通过设计来解决这个问题——通过实施来提高性能没有灵丹妙药。

于 2009-09-03T22:38:28.717 回答
1

有什么方法可以调用单个辅助方法,该方法接受关于您想要调用所需方法多少次的参数?跨 AppDomain 调用性能因实现而异。我相信在 CLR 4.0 中它可能会更好,但我并不完全精通那里的细节。

通常,您希望通过辅助方法“批处理”调用来避免开销。

于 2009-07-17T16:50:15.943 回答
0

我看到了同样的结果。我无法解释为什么它要慢得多,只是它比运行两个不同的进程并相互通信要快。在我的设计中,我面临着类似的困境。最后,我修改了我的设计以创建独立的应用程序域;应用程序域能够完成其工作,而无需在执行期间与另一个应用程序域通信......它只会在完成时报告数据。

于 2009-08-19T10:46:08.310 回答