Linux中静态库的制作与使用

0. 库的基本概念

0.1 什么是库

  • 在Windows和Linux下都大量存在着库。
  • 库文件是计算机上的一类文件,可以简单的把库文件看成一种代码仓库(二进制代码),本质上来说库是一种可执行代码的二进制形式,它提供给使用者一些可以直接拿来用的变量、函数或类,可以被操作系统载入内存执行。
  • 库是特殊的一种程序,编写库的程序和编写一般的程序区别不大,只是库不能单独运行。
  • 由于Windows和Linux的平台的不同(主要是编译器、汇编器和链接器的不同),因此二者库的二进制是不兼容的。

0.2 Linux中库的种类

在Linux中,库文件有两种,静态库动态库(共享库)。它们的区别是在于代码被载入的时刻的不同:

  • 静态库在程序的链接阶段被复制到了程序中,体积较大;
  • 动态库在链接阶段没有被复制到程序中,而是可执行程序在运行时由系统动态加载到内存中供程序调用,因此代码体积较小。

0.3 库的好处

  1. 代码保密。
  2. 方便部署和分发。
  3. 库是别人写好的现有的、成熟的、可以复用的代码,可以使用但要记得遵守许可协议。
  4. 不同的应用程序 如果调用相同的库,那么在内存里只需要有一份该动态库的实例。

1. 静态库的命名规则

在Linux系统中,静态库(库文件)的命名格式为:libxxx.a。其中:

  • lib:前缀(固定)
  • xxx:库的名称(自己起的)
  • .a:后缀(固定)

2. 静态库的制作

2.1 静态库的制作过程

  1. 通过gcc编译器将源文件编译生成若干.o文件。
  2. 使用ar工具(archive)完成对.o文件的打包。
    命令格式为
    ar rcs libxxx.a xxx.o xxx.o
    其中:
    - r:将文件插入备存文件中
    - c:建立备存文件
    - s:建立索引

2.2 静态库的制作过程示例

情景如下:我们写了若干个.c代码,这些.c代码组合起来能够完成一个计算器的功能。其中,add.c、div.c、mult.c、sub.c为计算器的核心代码,要将他们生成为一个静态库。
在这里插入图片描述

2.2.1 通过gcc编译器生成若干.o文件

通过命令行进入calc文件。
在这里插入图片描述
输入如下命令,将四个.c代码经过预处理、编译和汇编,生成.o文件。

gcc add.c div.c mult.c sub.c -c 

生成结果如下所示:
在这里插入图片描述
注:

  • 为什么不对head.h进行-c操作,因为在对四个.c文件进行-c时,在预处理阶段已经把头文件的内容包含进.i文件内了。
  • 为什么不对main.c进行-c操作,因为main.c文件是测试代码,不需要加进静态库内。

2.2.2 对.o文件打包

由于要生成的静态库是具有计算器功能的,因此设定库文件(静态库)的名称为libcalc.a。

依然在calc目录下,输入如下命令,进行.o文件的打包,生成名为libcalc.a的静态库。

ar rcs libcalc.a add.o div.o mult.o sub.o

生成的静态库如下图所示。
在这里插入图片描述
至此,就完成了静态库的制作。

3. 静态库的使用

首先给出要使用静态库的文件的树形结构图。
在这里插入图片描述
如下是main.c、add.c、div.c、mult.c、sub.c的内容。
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
可见,main.c中没有使用的四个函数的定义,不是一个完整的程序;而add.c、div.c、mult.c、sub.c中,没有main函数入口,因此也不是一个完整的程序。如果单独对这个五个.c文件使用gcc -o进行编译链接,都将报错。

因此,可以通过将add.c、div.c、mult.c、sub.c创建为静态链接库libcalc.a,使得main.c调用四个函数时可调用静态链接库。

依照2. 静态库的制作,将add.c、div.c、mult.c、sub.c创建为静态链接库。如下图所示,先制作.o文件。
在这里插入图片描述
发现编译链接过程出错,由于在预处理阶段需要将head.h文件的内容包含进去,但是head.h与这四个.c文件不在同一目录下,因此程序报错。

输入cd ..返回上一级,然后输入tree命令,可以查看文件结构,发现head.h文件位于include文件夹中。
在这里插入图片描述
因此在对四个.c文件进行编译链接操作时,需要输入如下命令。其中:

  • 参数-I(大写的i)的意思是指定头文件的搜索目录;
  • ../的意思是:一个.表示当前目录,..表示上一级目录,../include表示在上一级目录中进入include文件夹内。
gcc add.c div.c mult.c sub.c -c -I ../include/

编译链接成功通过,并生成四个对应的.o文件。
在这里插入图片描述
接着,通过如下命令,制作静态库。

ar rcs libcalc.a add.o div.o mult.o sub.o

生成的静态库如下图所示。
在这里插入图片描述
然后通过如下命令,将libcalc.a这个静态库文件,移动到lib文件夹内。

mv libcalc.a ../lib/

移动之后,library文件夹的树形结构图如下图所示。
在这里插入图片描述
最后一步,也就是使用静态库。输入如下命令,对main.c文件进行编译链接。其中:

  • -o app的意思是指定输出文件的文件名为app,此时由于未输入类似于-c的命令,因此直接编译链接生成可执行文件app;
  • -I ./include/的意思是,指定头文件的搜索目录为当前路径下的名为include的文件夹内;
  • -L ./lib的意思是,指定编译的时候,搜索的库的路径为lib文件夹内;
  • -l calc的意思是,在程序编译的时候,指定使用的库的名称为calc。(这里要注意区分,calc为库的名称,libcalc.a为静态库(库文件)的名称。)
gcc main.c -o app -I ./include/ -L ./lib/ -l calc

编译链接成功后,文件内容如下图所示。可以看到,生成了名为app的可执行程序。至此就完成了静态库的使用。
在这里插入图片描述
输入如下命令,运行app。

./app

运行结果如下图所示。
在这里插入图片描述

4. 静态库的分发

在制作好了静态库之后,如果需要将静态库分发给别的开发者时,需要注意,既要发送libcalc.a这个静态库文件,又需要发送与之对应的头文件head.h。

因为libcalc.a中仅仅包含了函数的定义,而函数的声明在head.h中。如果想要正常使用库文件中的函数,还需要函数的声明,因此头文件需要与库文件一并发送。

  • 2
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

吮指原味张

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值