zoukankan      html  css  js  c++  java
  • 函数库管理——动态函数库与静态函数库

    静态函数库与动态函数库基本认知:

    GCC编译基础流程包括:预处理、编译、汇编、链接。注意在特定语义环境中区别第一个编译和第二个编译的含义。

    静态链接:链接器在链接时将库的内容加入到可执行程序中

    动态链接:链接器在链接时仅仅建立与所需库函数之间的链接关系,在程序运行时才将所需资源调入可执行程序中

    静态函数库(静态链接库):程序编译时使用

      被称作:archive

      扩展名:.a

      命名格式:libxxx.a

      独立执行:编译成功的可执行文件可以独立执行

      升级难易度:难

    动态函数库(动态链接库):程序运行时使用

      被称作:shared object

      扩展名:.so 

      命名格式:libxxx.so

      独立执行:编译成功的可执行文件不可独立执行,库函数文件必须要存在,并且函数库所在目录也不能改变

      升级难易度:易

    注:使用gcc hello.c -o hello时,系统默认使用动态链接方式进行编译程序,若想使用静态编译,需加入-static参数

      如果静态库、动态库都放在/lib下,当静态库函数与动态库函数重名时,系统也是优先考虑链接动态库,同样如果想要使用静态库,需加入-static选项

     

    静态函数库与静态函数库的制作与使用:

    实例程序:

    "mylib.c"

    #include "mylib.h"

    int sub( int a, int b )
    {
            return a - b;
    }
    int add( int a, int b )
    {
            return a + b;
    }

     

    "mylib.h"

    #ifndef __MYLIB_H__
    #define __MYLIB_H__

    extern int sub( int, int );
    extern int add( int, int );

    #endif

     

    "hello.c"

    #include <stdio.h>
    #include "mylib.h"

    int main( void )
    {
            printf( "100 - 20 = %d ", sub( 100, 20 ) );
            printf( "100 + 20 = %d ", add( 100, 20 ) );
            return 0;
    }

    静态函数库的制作步骤:

      (1)#gcc -c mylib.c -o mylib.o    //编译目标文件

      (2)#ar  rc  libmylib.a  mylib.o    //制作静态库

     静态函数库的使用:

      库函数和头文件都在当前目录下:

      #gcc  -o hello  hello.c  libmylib.a

      或者

      #gcc  -o hello  hello.c  -L /home/zhu/program/  -lmylib           //  /home/zhu/program/为当前目录

      上面两种方式都可以成功。

      库函数和头文件不在当前目录下:libmylib.a移动到/home/zhu/lib/    mylib.h移动到/home/zhu/include/

       #gcc -o hello hello.c -I /home/zhu/include/ -L /home/zhu/lib/ -lmylib

      上述编译过程都没有加入-static选项,所以默认都是采用动态链接(dynamically linked)。加上-static后才是静态链接(statically linked)的。用静态库既可以实现静态链接也可以实现动态链接。用file命令查看hello,确实可执行文件大小有差别。奇怪的是,对于这里的动态链接,即使把libmylib.a删除,hello照样可以运行。动态链接不是没有将库函数链接进入可执行文件里吗??

      编译程序时,编译器默认会到/lib/、/usr/lib/下查找库函数,到/usr/include/下查找头文件。如果我们把libmylib.a放到/lib/或者/usr/lib/,把mylib.h放到/usr/include/目录下,那么编译时就不需要再加上选项 -I /home/zhu/include/ 和 -L /home/zhu/lib/

    可以直接写成:#gcc -o hello hello.c  -lmylib

     

    动态函数库的制作:

      #gcc -shared  mylib.c  -o  libmylib.so

    动态函数库的使用:

      库函数、头文件都在当前目录下:

      # gcc -o hello hello.c libmylib.so

      #./hello

      ./hello: error while loading shared libraries: libmylib.so: cannot open shared object file: No such file or directory

      需要把当前目录加入搜索路径:

      #export  LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/home/zhu/program

      或者把libmylib.so拷贝到/lib/、/usr/lib/中

      #./hello 运行成功  

     

      把libmylib.so移动到/home/zhu/lib/    mylib.h移动到/home/zhu/include/

      #gcc -static hello.c -o hello -I /home/zhu/include/ -L /home/zhu/lib/ -lmylib

      /usr/bin/ld: cannot find -lmylib

      动态库不能用静态编译

     

    把libmylib.so和libmylib.a同时放到/home/zhu/lib中:

      如果使用#gcc hello.c -o hello -I /home/zhu/include/ -L /home/zhu/lib/ -lmylib, 默认使用的是libmylib.so,并且编译成功后不可运行,要想运行必须将/home/zhu/lib/加入到LD_LIBRARAY_PATH中,或者将libmylib.so拷贝到/lib/或/usr/lib下。

      如果使用#gcc -static hello.c -o hello -I /home/zhu/include/ -L /home/zhu/lib/ -lmylib,则使用的是libmylib.a,并且编译成功后即可运行。

      

      

  • 相关阅读:
    巨人的崛起 Android操作系统发展历程
    iPhone 4S定位功能加强 支持GLONASS系统
    android子线程更新UI,与主Thread一起工作
    什么在阻碍移动互联网的普及?
    WEB.CONFIG 配置详解
    解决在aspx页面上进行传中文参数时会出现乱码问题
    VS2005水晶报表注册码
    windows2003应用程序池假死的问题
    浅谈ASP.NET内部机制
    合理建立数据库索引
  • 原文地址:https://www.cnblogs.com/nufangrensheng/p/3427529.html
Copyright © 2011-2022 走看看