如何确定不需要MarshalByRefObject的原因

时间:2015-03-21 18:04:31

标签: c# com-interop ole

COM过滤器类的实现(here)在MarshalByRefObject类和IDisposable接口上添加依赖关系,如下所示:

class MessageFilter : MarshalByRefObject, IDisposable, IMessageFilter

同样的MSDN implementation不使用这些:

class MessageFilter : IOleMessageFilter

我已经尝试了两种实现,但它们都有效。为什么MSDN实现不需要依赖项?由于涉及IOleMessageFilter接口使用的属性,它们是否可能被拉入?使用的属性是:

[ComImport()]
[Guid("00000016-0000-0000-C000-000000000046")]
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]

但这两种实现都使用了这些,所以我很困惑。这两种实现都指定了[DllImport("Ole32.dll")],但MSDN实现不包含随附的[PreserveSig]

2 个答案:

答案 0 :(得分:1)

IMO,MarshalByRefObject's implementation中的任何内容都没有什么特别之处,只有Object才能实现COM IMessageFilter(AKA IOleMessageFilter)。

或许,从StandardOleMarshalObject派生MessageFilter更合乎逻辑,因为(from here):

  

只有STA(APARTMENT_THREADED)线程可能有消息过滤器If   在初始化的线程上调用CoRegisterMessageFilter   使用COINIT_MULTITHREADED,返回代码为CO_E_NOT_SUPPORTED   (0x80004021

也就是说,我不确定StandardOleMarshalObject是否也是必需的,因为IMessageFilter方法应该仅在已注册COM消息过滤器的同一STA线程上调用。 / p>

您可以在我最近的问题中详细了解StandardOleMarshalObject vs Object

在Andrew Whitechapel的MSDN博客中:

Andrew Whitechapel在IMessageFilter本身也有一篇优秀的博客文章:

答案 1 :(得分:1)

COM是一种纯粹基于接口的编程范例。它完全不知道该类是什么样的,它所关心的只是它实现了IMessageFilter。这与接口在C#语言中的工作方式没有什么不同。

因此,如果程序员有充分的理由让这个类做的不仅仅是接收消息过滤器回调,那么这很好。我冒昧地猜测他实施了IDisposable来恢复旧的消息过滤器。解释MarshalByRefObject变得相当困难,你必须深入挖掘源代码以找到一个很好的理由。

COM的不同之处在于它完全不关心界面的名称。你可以随意调用它,唯一重要的是[Guid]。 IMessageFilter是MSDN文档中使用的名称,Visual Studio人员可能希望避免与.NET IMessageFilter类型发生冲突,它完全不同。

所以是的,你的班级工作正常是完全正常的。不要添加你不需要的任何东西。