【问题标题】:COM Dual InterfacesCOM 双接口
【发布时间】:2011-02-19 15:34:36
【问题描述】:

COM 中的双接口是能够通过 DispInterface 或 VTable 方法访问的接口。

现在谁能告诉我这两种方法到底有什么区别?

我认为 VTable 是一个虚拟表,它在实现具有可以在子类中覆盖的虚拟函数的类层次结构时保存指向不同函数的指针。但是我看不出这与 COM 中的双接口有什么关系?

【问题讨论】:

    标签: interface com idispatch


    【解决方案1】:

    主要区别在于调用对象方法的方式。如果 DispInterface 调用通过 IDispatch::Invoke 方法(在脚本中使用或在没有接口描述的情况下使用),请参阅remarks。这种方法比第二种选择慢得多。第二种情况直接使用VTable进行方法调用(用于C++或.NET语言的调用)

    【讨论】:

    • 那么IDispatch上的invoke方法是用来调用VBScript或JScript等脚本中的方法的?
    • @Tony 正确 - 如果您希望 COM 对象可从脚本中使用,您将需要一个双接口。
    • 是的,当你在脚本中调用一个方法时,它首先调用 IDispatch::GetIDsOfNames 然后 IDispatch::Invoke
    【解决方案2】:

    我只想回答托尼的其他问题。

    如果你想创建一个可以从 VBScript/JScript 或旧的“经典” ASP 访问的 COM,你必须实现 IDispatch。

    在 Visual Basic 6 或 MS Office 的 VBA 中,可以同时使用这两种方式。如果您将引用添加到您的 COM,那么您将使用“早期绑定”(IUnknown 或 VTable)。如果您在 VB6 或 VBA 中使用带有 CreateObject(“ProgIdName”)的 COM,您将使用“后期绑定”。

    理解使 COM 可以从 VB6/VBA 等访问是非常重要的。仅仅实现 IUnknown 接口是不够的。您必须使用oleautomation 属性创建和注册类型库。为此,您可以在您的 COM 接口中使用仅与oleautomation 兼容的数据类型(请参阅http://msdn.microsoft.com/en-us/library/aa367129%28VS.85%29.aspx)。为了理解类型库起到了客户端编组 DLL 的作用,因此它有助于像 VB6/VBA 这样的客户端软件将正确的数据作为参数发送到您的 COM。您不要忘记,即使您的 COM 将是一个 InProc 服务器、一个 DLL,参数也不会直接转发到 COM,而是需要编组。在封送处理期间,将在运行 COM 的线程上创建数据副本。它使您的 COM DLL 线程从一侧安全,如果调用您的 COM 方法的线程将在 COM 返回值之前结束,您的 COM 不会崩溃。

    可能我对封送处理的解释并不容易,但重要的是不要忘记创建和注册类型库,以便更好地保存为 COM 内部的资源。

    【讨论】:

      【解决方案3】:

      简而言之,COM 是二进制规范,而不是语言规范。双接口和代码中的派生类之间确实没有关联。苹果和橙子。

      VTable 是“早期绑定”的,因此速度更快。你知道你在编译时调用的方法的类型。

      使用 DispInterface 是“后期绑定”的,因此速度较慢,但​​更灵活。它广泛用于脚本编写。方法和属性类型在运行时确定。

      我希望这个简短的解释会有所帮助。

      【讨论】:

      • “二进制规范”到底是什么意思?
      • @Tony:这意味着 COM 只解决了组件在二进制级别上的通信方式——它没有说明组件是如何开发的,代码是用什么语言编写的,或者是否有一个“类”等级制度”。请参阅组件对象模型:技术概述@msdn.microsoft.com/en-us/library/ms809980.aspx
      猜你喜欢
      • 2010-11-22
      • 2011-02-07
      • 2012-08-20
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-07-23
      • 2011-06-27
      • 2010-10-20
      相关资源
      最近更新 更多