2010-06-29 76 views
15

让我们说我正在访问第三方库,文档指出我可以使用pInvoke或创建一个互操作库并使用COM。这两种技术有什么区别,为什么我可以选择一种呢?pInvoke和COM Interop有什么区别?

回答

12

P/Invoke用于调用普通的C API(像大多数的Win32 API)。 COM互操作用于调用COM对象。

你可以围绕一个C API创建一个C++ COM包装器,然后使用COM互操作来调用你的包装器,如果API调用的数量相对较高(并且你可以使用COM包装器将它们封装为一个或两个调用)。这是因为托管本机互操作性可能相对昂贵,并且最大限度地减少转换次数是很好的。尽管实际上我会说使用C++/CLI创建包装可能会对C#方面更友好一些(例如,查看SlimDX,例如,这是围绕COM API(DirectX)的C++/CLI包装)。除非你有一个特定的性能问题,否则我只会使用你试图调用的API更自然的方法:如果它是C API(如Win32 API),那么使用P/Invoke的。如果它是基于COM的,那么使用COM互操作。

+0

那么你是说引擎盖下,COM interops自己在做pinvokes吗?这个COM只是一个友好的包装? – Grant 2010-06-29 05:17:05

+2

不,COM互操作和P/Invoke是不同的,而另一个没有实现。我在第二段中说的是,如果C API是“chatty”并且需要大量函数调用,那么可以使用C++中的COM包装器并从C#中调用* wrapper *来减少managed-本地转换。我怀疑这是你的图书馆的文档建议。 – 2010-06-29 05:19:18

3

PInvoke使用动态链接机制将外部代码引入执行过程。动态链接库(DLL)必须与调用应用程序具有相同的目标体系结构,因此无法从64位到32位进行交叉调用,反之亦然。而是将DLL映射到调用者的地址空间并在执行过程中执行。

COM,DCOM,COM +和ActiveX都基于进程间通信库,但有时可能会转化为简单的DLL加载。 COM链接的对象与CORBA对象相关,但并不完全相同,但是当CORBA发展自己的对象定位器时,COM实现仍然松散地基于Sun Microsystems RPC和XDR库,扩展了COM的面向对象功能。 COM对象不是由DLL引用的,而是由用于查找对象类和查询其接口的GUID引用的。目标代码通常在单独的进程中运行,并可能在单独的服务器上运行。