如何在C语言中创建和使用静态和动态库
The purpose
在Linux上,可以创建两种类型的库,即静态库(.a)和动态库(.so),但在编译时需要使用相似的方法。也就是说,即使存在不同库的libA.a和libA.so,编译命令中省略了库的扩展名,如gcc xxx -lA,因此无法确定使用哪一个库。
我想要验证当libA.a和libA.so共存时的行为,并做些记录。
先提出结论
如果在命令中指定了库libA(使用-lA选项),则动态库libA.so将优先于静态库libA.a进行链接。
在中文中,原文的释义是:在追加说明中,通过指定“-static”的选项,可以链接静态库libA.a。
追加说明:
通过gcc -o main main.c -L. -static -lA这样的编译命令,可以链接静态库libA.a。
在编译命令中使用gcc的”-Wl”选项,通过指定”-Bdynamic”(动态)或”-Bstatic”(静态),可以选择库文件。非常感谢yumetodo先生的建议!
样本代码
使用下面这段代码。
此外,将num设置为5时使用静态库,将num设置为10时使用动态库,可以确定在编译时使用了哪一个。
在C语言中声明全局变量。
创建和验证动态库
#include<stdio.h>
#include"A.h"
void A(){
num = 10; //動的ライブラリでnumを10にする
printf("inside A, num = %d\n", num);
}
#Aの共有(動的)ライブラリを作成
[pirlo@centos8 02]$ gcc -shared -o libA.so -c A.c
・・・
#メイン処理をコンパイルして実行ファイルを作成
[pirlo@centos8 02]$ gcc -o main main.c -L. -lA -lB
#ファイル一覧
[pirlo@centos8 02]$ ls
A.c A.h B.c B.h libA.so libB.so main main.c
[pirlo@centos8 02]$ ./main
inside A, num = 10
inside B, num = 10
创建并验证静态库。
#include<stdio.h>
#include"A.h"
void A(){
num = 5; //静的ライブラリのここだけは違う
printf("inside A, num = %d\n", num);
}
#Aの静的ライブラリを作成
[pirlo@centos8 02]$ gcc -c A.c B.c #オブジェクト「.o」ファイルが作成される
[pirlo@centos8 02]$ ls
A.c A.h A.o B.c B.h B.o main.c
[pirlo@centos8 02]$ ar rcs libA.a A.o #オブジェクトファイルから静的ライブラリを作成
[pirlo@centos8 02]$ ls
A.c A.h A.o B.c B.h B.o libA.a main.c
・・・Bの関連処理を略・・・
#メイン処理をコンパイルして実行ファイルを作成(コマンドは動的の時と完全一致)
[pirlo@centos8 02]$ gcc -o main main.c -L. -lA -lB
#ファイル一覧
[pirlo@centos8 02]$ ls
A.c A.h A.o B.c B.h B.o libA.a libB.a main main.c
[pirlo@centos8 02]$ ./main
inside A, num = 5
inside B, num = 5
在存在动态和静态库共存的情况下,请再次确认。
#ファイル一覧
[pirlo@centos8 02]$ ls
A.c A.h A.o B.c B.h B.o libA.a libA.so libB.a libB.so main.c
#同じコンパイルコマンドで実行ファイルを再作成
[pirlo@centos8 02]$ gcc -o main main.c -L. -lA -lB
[pirlo@centos8 02]$ ./main
inside A, num = 10
inside B, num = 10
总结
如果动态和静态库同时存在,优先引用动态库。
如果添加”-static”选项,则会引用静态库。
[pirlo@centos8 02]$ ls
A.c A.h A.o B.c B.h B.o libA.a libA.so libB.a libB.so main.c
#「-static」オプション無し
[pirlo@centos8 02]$ gcc -o main main.c -L. -lA -lB
[pirlo@centos8 02]$ ./main
inside A, num = 10
inside B, num = 10
#「-static」オプション有り
[pirlo@centos8 02]$ gcc -o main main.c -L. -static -lA -lB
[pirlo@centos8 02]$ ./main
inside A, num = 5
inside B, num = 5
使用gcc的”-Wl”选项,可以通过指定”-Bdynamic”(动态)或”-Bstatic”(静态)来选择库。
#AとBの静的ライブラリを使用
[pirlo@centos8 02]$ gcc -o main main.c -L. -static-libgcc -Wl,-Bdynamic,-lc,-Bstatic,-lA,-lB
[pirlo@centos8 02]$ ./main
inside A, num = 5
inside B, num = 5
#すべての動的ライブラリを使用
[pirlo@centos8 02]$ gcc -o main main.c -L. -static-libgcc -Wl,-Bdynamic,-lc,-lA -lB
[pirlo@centos8 02]$ ./main
inside A, num = 10
inside B, num = 10
各个参考对象
请参考下面的内容创建一个动态库。
17.3 在GCC中创建动态库。
请参考以下内容来创建一个静态库。
17.4. 使用GCC和ar创建静态库。