【IT168专稿】 多年以来,大家似乎已习惯了受折磨于管理COM组件的多个版本,谢天谢地,直到微软免注册COM的出现,才总算结束了这种状态。
也许一直都梦想拥有可重复使用、动态链接的组件,因为它们可平衡代码量及节省内存——重复有人已经做过的东西好比再发明一次车轮,但成千上万的开发者仍使用着他们的本机DLL,且在文件版本及安装上也没有统一系统化的方法,开发者们经常面临要重写他们自己或其他人的DLL,通俗一点来说叫做“炒现饭”或“做无用功”。
也许这种日子即将永远离我们远去了,即便有了 .NET Framework的全局程序集缓存(GAC)、程序集清单、及托管代码组件,但事实上,我们仍在使用VB6的控件、C++活动模板库(ATL)、或ActiveX进行开发,而这种存在互操作的程序仍可能演变为某天某人的DLL Hell。DLL Hell,顾名思义,是对一种状态的通常描述,指当程序从一个DLL中加载或执行代码时,这个有着相同DLL文件名的文件,行为却与开发者预期的有所不同,也就是说,有着两个以上的同名DLL。大多数这种情况发生在安装程序复制并注册了一个较旧版本的DLL,取代了计算机中较新的版本,或是覆盖了一个同名的文件,还有一种较少见的情况,就是新版本的DLL中取消了向后兼容。
在任一情况中,原本工作正常的程序会突然退出,这是因为老版本的DLL不支持应用程序所要加载的新版本DLL中的函数,或是新版本的DLL去掉了以前版本中所支持的函数。
但如果客户机上运行的是Windows XP SP2、Windows Server 2003或更新的Windows操作系统,微软引入的免注册COM(Reg-free COM)就能减少或完全消除DLL冲突。本文主要介绍托管.NET代码下的免注册COM,及用XCOPY来部署COM组件。
免注册COM来了
为生成一个免注册COM的测试程序,先要解压与本文相关的ZIP文件:首先,打开WaveOutComControl解决方案并生成它;接下来,打开在/FlashCards_CSharp 目录中的FlashCards解决方案并重新生成它。这时,你会看到一个警告,没关系,可以安全地忽略它。从FlashCards的Debug目录中,复制FlashCards.exe两次,一次复制到/Reg目录中,一次复制到/RegFree目录中。
当你在生成解决方案时,Visual Studio会自动注册其中包含的WaveOut.ocx控件,为演示免注册COM,首先需要清除相关的注册表项(模拟成控件未注册的电脑),打开命令提示符,并输入以下命令卸载掉控件:regsvr32 /u WaveOut.ocx。
在执行完这些步骤之后,在/Reg与/RegFree目录中,会有示例程序“FlashCards”的两个副本。FlashCards是一个C# .NET 2.0的Windows Form(窗体)应用程序,它显示一些西班牙文及对应的英文翻译,它通过一个XPATH查询,从一个名为lesson1.xml的XML文件中读取单词,并随机显示出来;显示出来之后,FlashCards使用WaveOut.ocx ActiveX控件来播放相关单词的 .wav文件,让用户听到单词最地道的发音。WaveOut.ocx是一个使用C++和MFC编写的本机COM控件,示例程序演示了在不需要创建或修改任何注册表项的情况下,如何使用这个控件,换句话来说,你将看到支持免注册COM的Windows,是怎样加载及使用有着相同名字的多个DLL的。