什么是库

本质上来说库是一种可执行代码的二进制形式,可以被操作系统载入内存执行。由于windows和Linux的本质不同,因此二者库的二进制是不兼容的。Linux操作系统支持的库函数分为静态库和动态库,动态库又称共享库。Linux系统有几个重要的目录存放相应的库函数,如/lib,/usr/lib;头文件放在/usr/include。

什么是静态库

静态库的名字一般是libxxx.a;利用静态函数库编译成的文件比较大,因为整个函数库的所有数据都被整合进目标代码中,他的优点就显而易见了,即编译后的执行程序不需要外部的函数库的支持,因为所有使用的函数都已经被编译进可执行文件了。当然这也会成为他的缺点,因为如何静态函数库改变了,那么你的程序必须重新编译,而且体积也比较大。

什么是动态库

动态库的名字一般是libxxx.so,相对于静态函数库,动态函数库在编译的时候并没有被编译进目标代码中,你的程序执行到相关函数时才调用函数库里的相应函数,因此动态库函数所产生的可执行文件比较小。由于函数库没有被整合进你的程序,而是程序运行时动态申请并调用,所以程序的运行环境中必须提供相应的库。动态函数库的改变并不影响你的程序,所以动态函数库的升级比较方便。而且如果多个应用程序都要使用同一函数库,动态库就非常适合,可以减少应用程序的体积。

静态库的制作:

gcc -c file1.c

gcc -c file2.c

......

gcc -c fileN.c

ar -rcs libname.a file1.o file2.o ...... fileN.o

动态库制作:

gcc -shared -fpic -o libname.so file1.c file2.c  ...... fileN.c

编译:

动态库编译:gcc main.c -o test_li -Llib_patch -lname

静态库编译:gcc -static main.c -o test_li -Llib_patch -lname

(注:编译时出现提示错误:/usr/lib/ld:cannot find lc等错误查看链接:http://www.cnblogs.com/xiaohexiansheng/p/5500870.html)

案例:

 crypto.c
#include <stdio.h> void crypto(void)
{
printf("Start crypt..."); return ;
} crypto.h
#ifndef _CRYPTO_H_
#define _CRYPTO_H_ void crypto(void); #endif func.c
#include <stdio.h> void func(void)
{
printf("Start func..."); return ;
} func.h
#ifndef _FUNC_H_
#define _FUNC_H_ void func(void); #endif

生成静态库:

[xiaohexiansheng@centos6 test]$ ls
crypto.c  crypto.h  func.c  func.h  main.c
[xiaohexiansheng@centos6 test]$ gcc -c crypto.c -o crypto.o
[xiaohexiansheng@centos6 test]$ gcc -c func.c -o func.o
[xiaohexiansheng@centos6 test]$ ar -crs libcrypfunc.a crypto.o func.o
[xiaohexiansheng@centos6 test]$ ls
crypto.c  crypto.h  crypto.o  func.c  func.h  func.o  libcrypfunc.a  main.c

生成动态库:

[xiaohexiansheng@centos6 test]$ gcc -shared -fpic -o libcrypfunc.so crypto.c func.c
[xiaohexiansheng@centos6 test]$ ls
crypto.c  crypto.h  crypto.o  func.c  func.h  func.o  libcrypfunc.a  libcrypfunc.so  main.c

使用生成的动态库:

[xiaohexiansheng@centos6 test]$ gcc main.c -L. -lcrypfunc -o app

(注:-L指定函数库查找的位置,-L后面还有一个‘.’,表示在当前目录下寻找  -l指定库函数名,其中的lib和.a(.so)省略)
[xiaohexiansheng@centos6 test]$ ls
app  crypto.c  crypto.h  crypto.o  func.c  func.h  func.o  libcrypfunc.a  libcrypfunc.so  main.c
[xiaohexiansheng@centos6 test]$ ./app
./app: error while loading shared libraries: libcrypfunc.so: cannot open shared object file: No such file or directory
[xiaohexiansheng@centos6 test]$ pwd
/home/xiaohexiansheng/cc/library/test
[xiaohexiansheng@centos6 test]$ export LD_LIBRARY_PATH='/home/xiaohexiansheng/cc/library/test'
[xiaohexiansheng@centos6 test]$ ./app
Start crypt...Start func...[xiaohexiansheng@centos6 test]$

使用生成的静态库:

[xiaohexiansheng@centos6 test]$ ls
app  crypto.c  crypto.h  crypto.o  func.c  func.h  func.o  libcrypfunc.a  libcrypfunc.so  main.c
[xiaohexiansheng@centos6 test]$ gcc -static main.c -L. -lcrypfunc -o app
[xiaohexiansheng@centos6 test]$ ls
app  crypto.c  crypto.h  crypto.o  func.c  func.h  func.o  libcrypfunc.a  libcrypfunc.so  main.c
[xiaohexiansheng@centos6 test]$ ./app
Start crypt...Start func...[xiaohexiansheng@centos6 test]$

让我们看下静态库跟动态库的大小的区别:

[xiaohexiansheng@centos6 test]$ gcc main.c -L. -lcrypfunc -o sharedapp
[xiaohexiansheng@centos6 test]$ gcc -static main.c -L. -lcrypfunc -o staticapp

[xiaohexiansheng@centos6 test]$ du -sh sharedapp staticapp
8.0K    sharedapp
632K    staticapp

注意:

当静态库和动态库同时存在时,gcc默认使用的是动态库。如果强制使用静态库则加上-static选项。

动态库生成的可执行文件app不能正常运行是因为系统默认在/lib、/usr/lib下寻找动态库,如果想要程序正常运行可以把动态库放到这两个目录下的任意一个,或者按上面的那种方法 ---> LD_LIBRARY_PATH: 告诉系统执行程序的时候,除了/lib, /usr/lib以外还到哪里找动态库。

链接静态库的可执行文件比动态库的可执行文件要大很多。

参考链接:http://blog.chinaunix.net/uid-26833883-id-3219335.html

Linux 动态库 静态库的更多相关文章

  1. c/c++:动态库 静态库 linux/windows 例子 (转)

    作者:吴秦出处:http://www.cnblogs.com/skynet/本文基于署名 2.5 中国大陆许可协议发布,欢迎转载,演绎或用于商业目的,但是必须保留本文的署名吴秦(包含链接). C++静 ...

  2. 在Linux中创建静态库.a和动态库.so

    转自:http://www.cnblogs.com/laojie4321/archive/2012/03/28/2421056.html 在Linux中创建静态库.a和动态库.so 我们通常把一些公用 ...

  3. Linux 下动态库 / 静态库(依赖)

    一. 依赖动态库的动态库 libfun.so依赖动态库libtest.so(libfun.so动态库里的函数intnothing()调用了libtest.so里的intmytest()函数),而mai ...

  4. Linux库函数制作(静态库、动态库)

    Linux库函数制作(静态库.动态库) 静态库与动态库 链接方式 链接分为两种:静态链接.动态链接 静态链接: 由链接器在链接时将库的内容加入到可执行程序中 静态链接的特点是: 优点: 对运行环境的依 ...

  5. linux+vs2013编译静态库和动态库

    Linux下创建与使用静态库 Linux静态库命名规则 Linux静态库命名规范,必须是"lib[your_library_name].a":lib为前缀,中间是静态库名,扩展名为 ...

  6. linux 动态库 静态库 函数覆盖

    本文讨论了linux动态库  静态库中函数的覆盖问题. 测试目的: 同名函数,分别打成动态库libdync_lib.so与静态库libstatic_lib.a,并把libstatic_lib.a打到另 ...

  7. linux下的静态库和动态库

    一.linux下的静态库   静态库中的被调用的函数的代码会在编译时一起被复制到可执行文件中去的!!可执行文件在运行不需要静态库的存在!   二.linux下动态库的构建和使用 1.动态库的构建   ...

  8. linux下的静态库创建与查看,及如何查看某个可执行依赖于哪些动态库

    linux下的静态库创建与查看,及如何查看某个可执行依赖于哪些动态库   创建静态库:ar -rcs test.a *.o查看静态库:ar -tv test.a解压静态库:ar -x test.a 查 ...

  9. Linux中的静态库与动态库

    什么是库文件? 库文件是事先编译好的方法的合集.比如:我们提前写好一些数据公式的实现,将其打包成库文件,以后使用只需要库文件就可以,不需要重新编写. Linux系统中: 1.静态库的扩展名为.a:2. ...

随机推荐

  1. django执行sql

    http://docs.30c.org/djangobook2/chapter10/ def first_names(self, last_name): cursor = connection.cur ...

  2. 用Golang自己构造ICMP数据包

    ICMP是用来对网络状况进行反馈的协议,可以用来侦测网络状态或检测网路错误. 限于当前Golang在网络编程方面的代码稀缺,资料甚少,所以分享一个用Golang来构造ICMP数据包并发送ping程序的 ...

  3. python基础===socket模块的讲解(转)

    一.网络知识的一些介绍 socket 是网络连接端点.例如当你的Web浏览器请求www.jb51.net上的主页时,你的Web浏览器创建一个socket并命令它去连接 www.jb51.net的Web ...

  4. Guava Cache相关

    官方:http://ifeve.com/google-guava-cachesexplained/ 理解:https://segmentfault.com/a/1190000007300118 项目中 ...

  5. 配置Anaconda的jupyter notebook默认主页

    1. 在Anaconda Prompt里输:jupyter notebook --generate-config 然后找到这个文件:C:\Users\{YOUR NAME}\.jupyter\jupy ...

  6. 原型和JS内置对象

    原型 1.定义 每一个对象都有原型 原型仍然是一个对象 模拟实现面向对象的继承性 2.原型链 对象的原型还有原型 对象除了可以使用自有属性还可以继承原型上的属性 3.获取原型 对象.__proto__ ...

  7. request模拟知乎登录(无验证码机制)

    import request try: import cookielib #python2版本 except: import http.cookiejar as cookielib #python3版 ...

  8. C#格式化时间,货币

    1.格式化货币(跟系统的环境有关,中文系统默认格式化人民币,英文系统格式化美元) string.Format("{0:C}",0.2) 结果为:¥0.20 (英文操作系统结果:$0 ...

  9. Combo Box的简单使用(Win32)

    1 SendMessage函数向窗口发送消息 LRESULT SendMessage( HWND hWnd,     // handle to destination window UINT Msg, ...

  10. Selenium2+python自动化25-js处理日历控件(修改readonly属性)【转载】

    前言 日历控件是web网站上经常会遇到的一个场景,有些输入框是可以直接输入日期的,有些不能,以我们经常抢票的12306网站为例,详细讲解如何解决日历控件为readonly属性的问题. 基本思路:先用j ...