静态链接库与动态链接库

上传人:工**** 文档编号:558314568 上传时间:2022-08-24 格式:DOCX 页数:17 大小:37.52KB
返回 下载 相关 举报
静态链接库与动态链接库_第1页
第1页 / 共17页
静态链接库与动态链接库_第2页
第2页 / 共17页
静态链接库与动态链接库_第3页
第3页 / 共17页
静态链接库与动态链接库_第4页
第4页 / 共17页
静态链接库与动态链接库_第5页
第5页 / 共17页
点击查看更多>>
资源描述

《静态链接库与动态链接库》由会员分享,可在线阅读,更多相关《静态链接库与动态链接库(17页珍藏版)》请在金锄头文库上搜索。

1、介绍本文意在讲解静态链接库与动态链接库的创建与使用,在此之前先来对二者的概念、区别及 优缺点进行简要的阐述。其中大多内容参考相关网络资料,由于本人能力有限,不能确保完 全准确无误,若有偏差之处请不吝指出。文中使用到的代码均在Visual Studio 2008中编译 通过,如果您使用的IDE与本文不同,可根据实际情况进行相应项目创建与操作。希望本 文内容对您有所帮助。概念定义1. 分别编译与链接大多数高级语言都支持分别编译(Compili ng),程序员可以显式地把程序划分为独立的模 块或文件,然后由编译器(Compiler)对每个独立部分分别进行编译。在编译之后,由链接 器(Linker)把

2、这些独立编译单元链接(Linking)到一起。链接方式分为两种:(1)静态链接方式:在程序开发中,将各种目标模块(OBJ)文件、运行时库 (-LIB)文件,以及经常是已编译的资源(RES)文件链接在一起,以便创建Windows的EXE文件。(2)动态链接方式:在程序运行时,Windows把一个模块中的函数调用链接 到库模块中的实际函数上的过程。2. 静态链接库与动态链接库静态链接库(Static Library,简称LIB)与动态链接库(Dynamic Link Library,简称DLL) 都是共享代码的方式。如果使用静态链接库(也称静态库),则无论你愿不愿意八LIB文件 中的指令都会被直接

3、包含到最终生成的.EXE文件中。但是若使用.DLL文件,该.DLL文件中 的代码不必被包含在最终的.EXE文件中,.EXE文件执行时可以“动态”地载入和卸载这个 与.EXE文件独立的.DLL文件。2.1.动态链接方式链接一个DLL有两种方式:211载入时动态链接(Load-Time Dynamic Linking) 使用载入时动态链接,调用模块可以像调用本模块中的函数一样直接使用导出函数名调用 DLL中的函数。这需要在链接时将函数所在DLL的导入库链接到可执行文件中,导入库向 系统提供了载入DLL时所需的信息及用于定位DLL函数的地址符号。(相当于注册,当作 API函数来使用,其实API函数就

4、存放在系统DLL当中。)2.1.2 运行时动态链接(Run-Time Dynamic Linking)使用运行时动态链接,运行时可以通过LoadLibrary或LoadLibraryEx函数载入DLL。DLL 载入后,模块可以通过调用GetProcAddress获取DLL函数的入口地址,然后就可以通过返 回的函数指针调用DLL中的函数了。如此即可避免导入库文件了。2.2. 二者优点及不足221 静态链接库的优点(1) 代码装载速度快,执行速度略比动态链接库快;(2) 只需保证在开发者的计算机中有正确的LIB文件,在以二进制形式发布程 序时不需考虑在用户的计算机上LIB文件是否存在及版本问题,可

5、避免DLL地 狱等问题。222动态链接库的优点(1) 更加节省内存并减少页面交换;(2) DLL文件与EXE文件独立,只要输出接口不变(即名称、参数、返回值类 型和调用约定不变),更换DLL文件不会对EXE文件造成任何影响,因而极大 地提高了可维护性和可扩展性;(3) 不同编程语言编写的程序只要按照函数调用约定就可以调用同一个DLL函 数。223 不足之处(1) 使用静态链接生成的可执行文件体积较大,包含相同的公共代码,造成浪 费;(2) 使用动态链接库的应用程序不是自完备的,它依赖的DLL模块也要存在, 如果使用载入时动态链接,程序启动时发现DLL不存在,系统将终止程序并给 出错误信息。而使

6、用运行时动态链接,系统不会终止,但由于DLL中的导出函 数不可用,程序会加载失败;(3) 使用动态链接库可能造成DLL地狱。2.3. DLL 地狱DLL地狱(DLL Hell)是指因为系统文件被覆盖而让整个系统像是掉进了地狱。 简单地讲,DLL地狱是指当多个应用程序试图共享一个公用组件时,如某个DLL或某个组 件对象模型(COM )类,所引发的一系列问题。最典型的情况是,某个应用程序将要安装一个新版本的共享组件,而该组件与机器上的现有 版本不向后兼容。虽然刚安装的应用程序运行正常,但原来依赖前一版本共享组件的应用程 序也许已无法再工作。在某些情况下,问题的起因更加难以预料。比如,当用户浏览某些

7、 web站点时会同时下载某个Microsoft ActiveX控件。如果下载该控件,它将替换机器上原 有的任何版本的控件。如果机器上的某个应用程序恰好使用该控件,则很可能也会停止工作。在许多情况下,用户需要很长时间才会发现应用程序已停止工作。结果往往很难记起是何时 的机器变化影响到了该应用程序。这些问题的原因是应用程序不同组件的版本信息没有由系统记录或加强。而且,系统为某个 应用程序所做的改变会影响机器上的所有应用程序一现在建立完全从变化中隔离出来的应 用程序并不容易。三、静态链接库的创建与使用在此通过一个实例来介绍静态库的创建与使用。在该实例中,我们将一个实现两整数相加求 和的函数封装到静态

8、库中供其他程序调用。1.创建首先,使用Visual Studio 2008来创建一个带预编译头的静态库项目Static,该项目包含在 名为Library的解决方案中。1-1-创建静态库项目创建一个不带预编译头的静态链接库项目有以下几个步骤:(1) 单击菜单命令“文件”-“新建”-“项目”,弹出“新建项目”对话框;(2) 在弹出的“新建项目”对话框中,选择左边“类别”列表中选择“VisualC+” - “Win32”,在右边的“模版”中选择“Win32项目”;(3) 在下方输入项目名称“Static”,并选择项目创建的位置,勾选“生成解 决方案”,并输入解决方案名称“ Library”,然后点击

9、“确定”按钮;(4) 点击两次“下一步”按钮,进入“应用程序设置”界面;(5) 在“应用程序设置”界面中,选择“静态库”,并确保下方“附加选项” 中的“预编译头”被勾选,然后点击“完成”按钮。1.2. 编辑项目经过上面的步骤,初步创建了一个带预编译头的静态库项目,接下来编辑该项目以达到我们 的创建静态库的目的。首先添加一个用于定义导出函数的源文件Static.cpp,编码实现两个整数相加的Add函数。 源文件代码如下:#include “StdAfx.h”/ 标准头文件int Add(int a, int b)return a + b;接着点击菜单命令,“工具” “生成Static”如果一切顺

10、利的话,就会在解决方案的“Debug” 目录中生成了名为“Static.lib”的静态链接库。同时,需要给该静态链接库编写一个声明头文件Static.h,以便在链接时告知编译该链接库 中的导出函数声明。Static.h中的代码很简单,只要声明一下Add函数就可以:#ifndef _STATIC_H_/防止该头文件重复引用#defi ne _STATIC_H_int Add(int a, int b);/ 声明导出函数#e ndif接着点击菜单命令,“工具”-“生成Static”。如果一切顺利的话,就会在Library解决方 案的Debug目录中生成了名为MyDLL.lib的静态链接库。2.使用

11、在Library解决方案下,再添加一个Win32控制台应用程序空项目UseLIB。程序主文件名为UseLIB.cpp,其中包含用于调用Add函数的程序入口函数main。将刚才创建的Static.lib及其声明头文件Static.h 一同复制到UseLIB项目目录下。并在源文件UseLIB.cpp中使用预 编译命令链接Static.lib (也可以在IDE的项目属性中设置链接器选项,或者只复制Static.h 文件并设置UseLIB项目的“项目依赖项”为Static项目)。源文件UseLIB.cpp中的代码如下:#pragma comment(lib, “Static.lib”)/ 链接静态库

12、Static.lib#in clude vstdio.h#include “Static.h/包含Static.lib的声明头文件,声明导出函数Addint mai n(void)int a = 1, b = 2;printf(“d+%d=%dn, a, b, Add(a, b);/ 调用 Static.lib 中的 Add 函数return 0;接下来点击菜单命令,“工具”-“生成UseLIB”。如果顺利的话,就会在Library解决方案的Debug目录中生成了名为UseLIB.exe的可执行执文件,运行UseLIB.exe,将在控制台中输出结果:1+2=33.由于项目中创建的源文件为.CP

13、P文件,即C+源文件,因此Visual C+按C+规范,并 采用_cdecl调用约定对其进行编译。这样得到的导出函数就不能被C语言程序所调用。解 决该问题的办法是在函数体名称前添加extern “C修饰,告诉编译器,该函数按照C语言规 范,并采用_cdecl调用约定进行编译。因此源文件Add.cpp中的代码可修改如下:exter n “C int add(i nt a, int b)return a + b;最后重新编译该静态链接库项目,导出函数Add就能够被C语言程序所调用了。另一种不改变代码的方法是在“Static属性页”左边的列表中选择“配置属性”-“C/C+” -“高级”,然后在右边的

14、“调用约定”选择“_cdecl (/Gd)”,“编译为”选择“编译为 C+代码(/TP)”。这种方法在不同的IDE上设置方法有所不同。动态链接库的创建与使用在此同样通过一个实例来介绍动态链接库的创建与使用。在实例中,依然使用Add函数进 行讲解,这样一方面可以沿用上面静态链接的有关内容,另一方面也可以了解动态链接库与 静态链接库在创建和使用上的异同。1.创建首先,在之前创建的Library解决方案中添加一个带预编译头的动态链接库项目,项目名称 为Dynamic。使用不同IDE的朋友可以根据实际情况进行创建。1-1-创建动态链接库项目创建一个带预编译头的动态链接库项目有以下几个步骤:(1) 单击

15、菜单命令“文件”-“新建”-“项目”,弹出“新建项目”对话框;(2) 在弹出的“新建项目”对话框中,选择左边列表的“Visual C+” “Win32”, 在右边的项目模版中选择“ Win32项目”;(3) 在下方输入项目名称“Dynamic”,并选择项目创建的位置,然后点击“确 定”按钮;(4) 点击两次“下一步”按钮,进入“应用程序设置”界面;(5) 在“应用程序设置”界面中,选择“ DLL”,然后点击“完成”按钮。1.2.编辑项目Dynamic项目自动生成的dllmain.cpp源文件含有一个名为DllMain的函数,该函数是DLL 被链接时的入口函数,它由系统自动调用,在这里我们不用去理会它。与前面创建静态态链接库类似的,首先添加一个用于定义导出函数的源文件Dyn amic.cpp, 编码实现两个整数相加的Add函数。源文件代码如下:extern “C” _declspec(dllexport) int Add(int a,/声t明为 DLL 导出函数return a + b;与前面静态链接库不同,在Add函数体名称前不只添加了 extern “C”修饰,还多添加了一 个_declspec(dllexport)修饰。_declspec(dllexport)

展开阅读全文
相关资源
相关搜索

当前位置:首页 > 学术论文 > 其它学术论文

电脑版 |金锄头文库版权所有
经营许可证:蜀ICP备13022795号 | 川公网安备 51140202000112号