Linux IO编程——静态库、动态库

一、静态库

(一)静态库的介绍

静态库是在程序编译链接阶段 ,其代码会被完整地**"复制"到最终生成的可执行文件** 中,成为可执行文件的一部分,编译完成后,静态库与可执行文件"绑定",运行时无需额外依赖;

特点:可执行文件独立运行,不依赖外部库文件;静态库会使可执行文件体积较大,但是效率比较高;若静态库更新,需重新编译链接程序;

静态库文件格式:windows平台下为**.lib** ;Linux平台下为**.a**;Mac平台下为.a;

(二)静态库制作及使用

准备源文件:编写实现库功能的源文件(如 .c或 .cpp);

编译生成目标文件:将源文件编译成目标文件(如 .o或.obj) ;gcc -c 源文件.c -o 目标文件.o

bash 复制代码
gcc -c add.c -o add.o

打包生成静态库:使用归档工具将目标文件打包成静态库 ;ar -cr 静态库.a 目标文件.o

bash 复制代码
ar -cr libmyadd.a add.o

编译主程序并链接静态库,生成可执行文件 ;gcc 目标文件.o -l库名 -L库路径 -o 可执行文件

cpp 复制代码
gcc main.c -lmyadd -L. -o main

说明:如果库名是libmyadd.a,则库名是myadd,编译器会自动拼接lib前缀和.a后缀进行查找库文件。

bash 复制代码
./main

二、动态库

(一)动态库的定义

动态库也称之为共享库,是在程序运行时才被加载到内存 中,可以被多个可执行文件共享使用,为它们提供函数、数据等资源。

特点:可执行文件运行时,需依赖系统中存在的动态库;可执行文件体积小,有效节省磁盘和内存空间;更新灵活 ,只要接口不变,无需重新编译依赖它的可执行文件;

动态库文件格式:windows平台下为.dll;Linux平台下为.so;Mac平台下为.dylib;

(二)动态库的制作

准备源文件:编写实现库功能的源文件(如 .c或 .cpp);

编译生成与位置无关的目标文件 :使用编译器编译源文件时,添加相关选项(如GCC的-fPIC选项)生成位置无关代码(PIC)的目标文件;gcc -c -fPIC 源文件.c -o 目标文件.o

bash 复制代码
gcc -c -fPIC sub.c -o sub.o

链接生成动态库 :使用编译器将目标文件链接为动态库,多个程序可共享同一份动态库文件,节省内存;gcc -shared 目标文件.o -o 动态库.so

cpp 复制代码
gcc -shared sub.o -o libmysub.so

编译时通过 -L指定路径 、 -l指定库名 生成可执行文件;gcc 源文件.c -l库名 -L库路径 -o 可执行文件

bash 复制代码
gcc main.c -lmysub -L -o my_sub

运行时需通过 LD_LIBRARY_PATH 环境变量、 /etc/ld.so.conf 配置或系统路径,保证动态库可被加载;

  • 示例1:通过LD_LIBRARY_PATH环境变量运行 ;export LD_LIBRARY_PATH=$PWD (=后面就是库路径,PWD表示当前路径)

    bash 复制代码
    export LD_LIBRARY_PATH=$PWD
  • 示例2:通过**/etc/ld.so.conf 配置运行** ;编辑配置文件添加动态库路径:
    sudo vim /etc/ld.so.conf (在此文件中添加动态库路径)

    bash 复制代码
    pwd  #查看当前的绝对目录:/home/hqyj/IO/dynamic_library
    sudo vim /etc/ld.so.conf  #进入/etc/ld.so.conf,将当前路径加入


    添加完成之后,执行sudo ldconfig命令更新系统缓存

    bash 复制代码
    sudo ldconfig
  • 示例3:通过系统路径运行:优先考虑/usr/local/lib路径,然后进行更新系统缓存系统级库放/usr/lib,用户自定义库放 /usr/local/lib;

bash 复制代码
sudo mv libmysub.so /usr/local/lib
sudo ldconfig  #更新

三、静态库与动态库的区别

(1)链接方式:静态库在编译时链接,动态库在运行时链接;

(2)可执行文件体积:静态库使可执行文件体积大,动态库使可执行文件体积小;

(3)内存占用:多个程序使用同一静态库 时,每个程序都有一份库的副本 ,占用内存多 ;多个程序共享同一动态库 时,内存中只有一份库的副本,节省内存;

(4)更新维护:静态库更新需重新编译链接程序 ;动态库更新只需替换库文件,无需重新编译链接程序;

(5)依赖性:静态库无运行时依赖;动态库有运行时依赖,库缺失程序无法运行;

(6)适用场景:

  • 静态库:适合对程序独立性要求高,库不常更新,且对可执行文件启动速度有要求的场景;
  • 动态库:适合库需要频繁更新 ,多个程序共享库功能,且希望减小可执行文件体积的场景;

四、库制作常见问题及解决方案

(一)静态库链接时提示未定义的引用

可能原因:库文件路径错误、库名拼写错误、库中确实不存在该函数或变量的定义;

解决方法:检查库路径和库名是否正确,确认库中是否实现了所需功能;

(二)动态库运行时提示无法找到库文件

可能原因:库文件路径未加入系统默认搜索路径或者是未通过环境变量指定;

解决方法:将动态库复制到系统默认库路径(如/usr/local/lib),或设置相应的环境变量(如Linux的LD_LIBRARY_PATH);

(三)动态库版本冲突

可能原因:程序依赖的动态库版本与系统中安装的版本不一致;

解决方法:安装程序所需版本的动态库,或重新编译程序使其适配系统中的库版本;

相关推荐
别动我齐刘海7 小时前
C++ 工程化学习
java·linux·前端·c++·学习·机器学习·机器人
玖石书9 小时前
Ubuntu 24.04 UFW 全命令攻略:从入门到端口开放实战
linux·运维·ubuntu
xiaoqiMikko9 小时前
Linux 实战(七):useradd、sudoers、umask、SGID、软链 —— 三台真机实测
linux·centos
拂拉氏11 小时前
【知识讲解】 Linux之动静态库的了解
linux·运维·服务器·动静态库
Fcy64811 小时前
Linux下 五种IO模型的认识与⾮阻塞IO的实现
linux·服务器·io
Mikko712 小时前
Linux 重启后日志没了?进程被 OOM 杀了去哪看?logrotate 之后日志还往旧文件写?三台真机实测日志与性能排查
linux·运维·centos
书生执笔画浮沉12 小时前
分享一个开源小工具CAdapt
linux·c·gnu·glibc·kernel·升级·灵感
mounter62512 小时前
Linux 内核热升级(Live Update)技术详解:PCI、VFIO 与 IOMMU 子系统的演进与实战解析引言
linux·linux kernel·kernel·iommu·vfio
砚凝霜13 小时前
【软考信息安全】第十九章 Unix/Linux安全分析与防护
linux·安全·unix
creator_Li13 小时前
Linux 的 Page Cache
linux·page cache