🔥码云GVP开源项目 12k star Uniapp+ElementUI 功能强大 支持多语言、二开方便! 广告
[TOC] # 概念 我们开发时候经常有一些公共代码是需要反复使用,就把这些代码编译为库文件 库可以简单看成一组目标文件的集合,将这些目标文件经过压缩打包之后形成的一个文件.像在windows这样的平台上,最常用的c语言库是由集成按开发环境所附带的运行库,这些库一般由编译厂商提供 # windows下静态库创建和使用 ## 创建 1. 创建一个新项目,在已安装的模板中选择"常规",在右边的类型下选择"空项目",在名称和解决方案名称中输入staticlib.点击确定 2. 在解决方案资源管理器的头文件中添加mylib.h文件,在源文件添加mylib.c文件(即实现文件) ![](https://box.kancloud.cn/6e96a33dc9f35707ec597733977ae41d_372x302.png) 3. 在mylib.h文件中添加如下代码 ~~~ #pragma once #ifdef __cplusplus extern "C" { #endif int myAdd(int a, int b); #ifdef __cplusplus } #endif ~~~ 4. 在mylib.c文件中添加如下代码 ~~~ #include "mylib.h" int myAdd(int a, int b) { return a + b; } ~~~ 5. 配置项目属性.因为这是一个静态链接库,所以应在项目属性的"配置属性"下选择"常规",在其下的配置类型中选择静态库(.lib) ![](https://box.kancloud.cn/97fe73ee959fa40b3b7ee9631d9a0eaa_1582x908.png) 6. 编译生成新的解决方案,在Debug文件夹下会得到mylib.lib(对象文件库),将该.lib文件和相应头文件.h给用户,用户就可以使用该库里的函数了 ![](https://box.kancloud.cn/424e4f78c1b26acdc190783bf31f347e_600x230.png) 文件在这里 ![](https://box.kancloud.cn/08f839b5c8eb68b20f23b3fc45460b46_1084x296.png) ## 使用 方法一: 配置项目属性 A. 添加工程的头文件目录:工程-属性-配置属性-c/c++--常规--附加包含目录:加上头文件存放目录 B: 添加文件引用的lib静态库路径:工程--属性--配置属性--链接器--常规--附加库目录:加上lib文件存放目录 C: 然后添加工程引用的lib文件名:工程--属性--配置属性--链接器--输入--附加依赖项:加上lib文件名 方法二: 使用编译语句 ~~~ #pragma comment(lib, "./mylib.lib") ~~~ 方法三: 添加工程 就像你添加.h和.c文件一样,把lib文件添加到工程文件列表中去. 切换到"解决方法视图"-->选中要添加lib的工程-->点击右键-->添加-->现有项-->选择lib文件-->确定 测试下 ~~~ #define _CRT_SECURE_NO_WARNINGS #include<stdio.h> #include<string.h> #include<stdlib.h> #include"mylib.h" int main() { int a = 10; int b = 20; int ret = myAdd(a, b); printf("%d\n", ret); system("pause"); return EXIT_SUCCESS; } ~~~ ## 优缺点 * 静态库对函数库的链接是放在编译时期完成的,静态库在程序的链接阶段被复制到了程序中,和程序运行时没有关系 * 程序在运行时与函数库再无瓜葛,移植方便 * 浪费空间和资源,所有相关的目标文件与牵扯到的函数库被链接合成一个可执行文件 空间浪费是一个问题,另一个问题是静态链接对程序的更新,部署和发布也会带来很多麻烦.比如程序中使用的mylib.lib是由一个第三方厂商提供的,当该厂商更新容量mylib.lib的时候,那么我们的程序就要拿到最新版的mylib.lib,然后将其重新编译进我们的代码 # windows下动态库创建和使用 等程序运行的时候才链接,把链接过程推迟到了运行时再进行 ## 创建 1. 创建一个新项目,在已安装的模板中选择"常规",在右边的类型下选择"空项目",在名称和解决方案名称中输入mydll点击确定 2. 在解决方案资源管理器的头文件中添加mydll.h,在源文件添加mydll.c文件(即实现文件) 3. 在mydll.h文件中添加如下代码 ~~~ #pragma once #ifdef __cplusplus extern "C"{ #endif // __cplusplus //内部函数,外部函数 //外部函数.要声明,不声明只能内部使用 __declspec(dllexport) int myAdd(int a, int b); #ifdef __cplusplus } #endif // __cplusplus ~~~ 4. 在mydll.c文件中添加如下代码 ~~~ #include"mydll.h" int myAdd(int a, int b) { return a + b - 10; } ~~~ ![](https://box.kancloud.cn/4d0769363f5dffc678bf603905f0196c_1196x652.png) ![](https://box.kancloud.cn/027692b4644c82c292a31e44f2ecc0e4_678x380.png) **他会生成个lib文件,这个lib文件和静态库不同的地方在于,静态库的lib是实现,动态库是那些实现是导出的 dll是真正代码实现** 把lib,dll,.h文件拷贝出来 ## 使用 方法一: 隐式调用 创建主程序TestDll,将mydll.h, mydll.dll和mydll.lib复制到源代码目录下.(ps: 头文件Func.h不是必须的,只是c++中使用外部函数时,需要先进行声明)在程序中指定链接引用链接库 ~~~ #pragma comment(lib, "./mydll.lib") ~~~ 方法二: 显示调用 ~~~ HANDLE hDll; //声明一个dll实例文件句柄 hDll = LoadLibrarv("mvdll.dll"); //导入动态链接库 MYFUNC minus_test; //创建函数指针 //获取导入函数的函数指针 minus_test = (MYFUNC)GetProcAddress(hDll, "myminus"); ~~~