当前位置: 首页 > news >正文

外贸整合营销网站如何快速开发手机app

外贸整合营销网站,如何快速开发手机app,淘宝推广引流方法有哪些,多个域名绑定同一个网站vb6编绎COM DLL(ACTIVEX对象)时,选择工程兼容,二进制兼容的区别是什么?为什么某个接口函数的参数类型改了就不兼容了?总结:想要保持相同的DLL 类型库ID (TypeLib ID),工程兼容,修改类后CLSID会发生改变二进制兼容&…

vb6编绎COM DLL(ACTIVEX对象)时,选择工程兼容,二进制兼容的区别是什么?为什么某个接口函数的参数类型改了就不兼容了?

总结:想要保持相同的DLL 类型库ID (TypeLib ID),工程兼容,修改类后CLSID会发生改变

二进制兼容:TypeLib ID,CLSID都保持一样,但实际上接口发生了改变,也不一定能直接替换DLL


这是一个非常经典且重要的VB6 COM开发问题。我们来详细解释一下。

1. 无兼容 vs. 工程兼容 vs. 二进制兼容

这三种设置在编译COM DLL(ActiveX DLL)时,决定了VB6如何处理你的组件的全局唯一标识符(GUID),主要包括:

  • 类ID (CLSID): 每个类的唯一标识。

  • 接口ID (IID): 每个类的默认接口(_ClassName)的唯一标识。

  • 类型库ID (TypeLib ID): 整个组件的类型库的唯一标识。


无兼容 (No Compatibility)
  • 行为: 每次编译时,VB6都会为所有GUID(CLSID, IID, TypeLib ID)生成全新的、随机的值

  • 后果: 每次编译出来的DLL都是一个“全新”的组件。之前使用旧版本DLL的客户端程序(如EXE文件或其他DLL)将无法识别这个新版本,因为它们寻找的是旧的GUID。这会导致“类未注册”或“不兼容接口”的错误。

  • 使用场景: 仅在初始开发阶段,或者你确定没有其他程序在使用这个组件时使用。一旦组件被发布,就绝对不应该再使用此选项。


工程兼容 (Project Compatibility)
  • 行为: VB6会保留类型库ID (TypeLib ID),但会为新的或修改过的类和接口生成新的CLSID和IID。未修改的类会保持其原有的GUID。

  • 后果: 它允许你在VB6的集成开发环境(IDE)中调试当前工程(例如,一个测试用的EXE工程引用并调用这个DLL)而不会因为GUID改变而中断。然而,编译出来的DLL与之前版本是二进制不兼容的。如果你用这个DLL去覆盖已发布的版本,所有引用旧版DLL的已编译客户端程序都会崩溃。

  • 使用场景: 主要用于开发阶段的调试。它让你能一边修改DLL,一边在IDE里测试调用它的其他工程,而无需 constantly re-registering the DLL or breaking the reference in the IDE. 但绝对不能用于生成发布版本


二进制兼容 (Binary Compatibility)
  • 行为: VB6会尽力保留所有原有的GUID(CLSID, IID, TypeLib ID)。它会读取你指定的“旧版本DLL”文件,并确保新编译的DLL中,所有未更改的类和接口都使用完全相同的GUID。即使是新添加的类和接口,其GUID的生成也是基于旧类型库的种子,以确保一致性。

  • 后果: 这是实现版本兼容的关键。客户端程序无法区分新旧DLL,它们可以无缝工作。只要保持了兼容性,新DLL就可以直接替换旧DLL。

  • 使用场景: 用于维护和发布更新。当你需要修复bug或为现有接口添加新方法(而不修改旧方法)时,必须使用此模式来确保不会破坏现有的客户端应用程序。


2. 为什么修改接口参数类型会导致不兼容?

这涉及到COM的核心原则:接口的永恒性和不变性

  1. 接口即契约: 一个COM接口一旦发布,就是一个不可更改的契约。客户端程序在编译时,就根据这个契约生成了代码。例如,它知道MyMethod的第一个参数是一个4字节的Long,并且会按照这个约定来调用。

  2. 虚拟函数表 (vTable): COM调用是通过vTable来进行的。vTable是一个函数指针数组。客户端程序调用MyMethod时,实际上是调用vTable中第N个位置的函数。

  3. 二进制层面: 当你将参数从 Long (4字节) 改为 String (字符串的BSTR指针,也是4字节但含义完全不同) 或 Double (8字节) 时,你在二进制层面改变了这个函数的签名

    • 调用者(客户端)会按照旧的契约,传入一个 Long 值。

    • 而被调用者(你的新DLL)却期望接收一个 String 或 Double

    • 这会导致栈错误(stack corruption)或访问冲突(access violation),因为双方对参数的解释完全 mismatch,最终导致程序崩溃。

  4. GUID的作用: 每个接口的IID正是这个“契约”的唯一指纹。即使你只修改了一个参数的类型,在VB6看来,你已经彻底改变了这个接口。为了安全起见,VB6的“二进制兼容”模式会检测到这种破坏性更改,并警告你“IDL 特性不兼容”或类似的错误,拒绝保持原有的IID。它会强制生成一个新的IID。

    这样,客户端程序(寻找旧IID)就无法找到这个被“破坏”的接口,从而避免去调用它,防止了崩溃。这是一种“ fail-fast”的保护机制。虽然它导致了不兼容,但这比让程序随机崩溃要好得多。

总结与最佳实践

模式GUID 行为用途风险
无兼容全部重新生成初始开发高,绝对会破坏客户端
工程兼容保留部分,改变部分IDE内调试高,编译后的客户端会崩溃
二进制兼容尽力保留全部发布和更新低(如果遵守规则)

最佳实践:

  1. 一旦发布,永不更改: 绝对不要修改已发布接口(类的默认接口)的现有属性或方法的名称、参数类型、参数顺序或返回类型。

  2. 只增不减: 如果要扩展功能,只能向接口的末尾添加新的方法或属性。绝不能删除或插入到中间,这会改变vTable的顺序。

  3. 始终使用“二进制兼容”: 发布后,编译任何更新版本时都必须使用“二进制兼容”模式,并指向最近一个已发布的版本(.dll 或 .olb 文件)。

  4. 版本号管理: 当你进行兼容性更新时(如添加新方法),增加次版本号(如1.0.0 -> 1.1.0)。当你进行不兼容的更改时(迫不得已时),必须增加主版本号(如1.0.0 -> 2.0.0),并接受客户端需要重新编译的事实。

  5. 使用多接口: 对于重大的功能变更,更好的方法是定义一个新的接口(创建一个新的类),让客户端代码逐步迁移到新接口上,而不是破坏旧的接口。

所以,你遇到的情况正是VB6和COM机制在正常工作,保护你免于发布一个会导致现有应用程序崩溃的版本。

http://www.dtcms.com/a/601266.html

相关文章:

  • 谢赛宁×李飞飞×LeCun联手重磅|Cambrian-S:「视频空间超感知」新范式,实现真正持续视频感知
  • 在服务器网站上做跳转网站运营推广方式
  • Ansible 安装与入门
  • VMMap 学习笔记(8.7):命令行模式与自动抓取——无界面采集内存证据的正确姿势
  • 大型网站服务器得多少钱app大全免费软件排行榜
  • AXI-5.3.2~5.3.5
  • Anaconda安装与配置:构建人工智能开发环境
  • 从入门到精通:周志华《机器学习》第一、二章深度解析
  • 网站建设品牌策划装修设计软件排名
  • 社区投稿 | Oinone应用于整车制造供应链决策
  • 加强网站建设的制度网站网址怎么找
  • 【Git】Git04:分支管理
  • R语言用什么编译器 | 如何选择最适合你的R语言开发环境
  • cuda12 cudnn9 tensorflow 显卡加速
  • 网站建设目标的文字嘉兴企业网站排名
  • 手机网站开发语言选择怎么能在网上卖货
  • 编程算法学习
  • 在Beego框架中创建Services层
  • PPT插入的音乐怎么让它播放到某一页就停?
  • 打包,压缩解压,上传下载
  • 【动态规划】专题完结,题单汇总
  • 微信公众好第三方网站怎么做wordpress订阅关闭
  • 网站logo上传建筑室内设计软件
  • Linux环境下Nginx核心总结与密码验证实践
  • python实战:装饰模式详解
  • 一个基于TCP/IP接收数据并通过API推送数据的小工具
  • 经典网站建设案例wordpress讨论区插件
  • 具身记忆大展拳脚
  • Java语言编译器 | 深入了解Java编译过程与优化技巧
  • 实时开发平台(Streampark)--Flink SQL功能演示