函数库是为代码复用建立的,将同一类型,需要在不同的程序里使用的函数放置在一起,就组成了一个函数库。如 C 语言的标准库,它集合了开发者常用的函数。开发者自行编写的函数也可以组成函数库,通常称之为自定义函数库。C 语言的函数库以源代码的形式放在头文件里,较大的函数库可能会用到多个文件,因此涉及到编译的问题。本节将讨论用文件组成函数库的问题。

5.6.1 程序文件的大小

C 语言编译器允许分别编译,为每个文件生成以“.o”为后缀的目标文件,最后执行链接过程生成可执行文件。将一个程序放在一个大文件中,或者分拆成多个较小的文件,所得到的结果其实是相同的。编译器编译一个大文件比编译由这个大文件拆分而成的一系列小文件所花费的时间要长,对成员员来说,小文件更容易阅读和理解,所以应该把大文件拆分为一系列小文件编写。而且如果修改程序时只修改了其中一个文件,那么编译时也只需要重新编译修改过的文件,再执行连接过程生成可执行文件,这样能缩短程序编译的总时间。

5.6.2 分类组织文件

在开发大型程序时,很容易迷失某个具体功能点在源代码中的位置。如果在程序设计的早期预先估计程序的规模,将同一类型的函数放在同一个文件中,以有意义的名字为函数和文件命名,编写详细的注释,则可以最大程度避免该问题。如下例所示的多个文件。

(1)主程序文件 exercise.c:

#include <stdio.h>
#include "rate_compute.h" // 包含用户自定义的函数库 rate_compute.h int main()
{
...
simple_interest(); // 调用函数库 rate_compute.h 中的函数
compound_interest(); // 调用函数库 rate_compute.h 中的函数
...
}

(2)包含所有利率计算函数原型的头文件 rate_compute.h:

#ifndef RATE_COMPUTE_H_			// 判断是否未定义标识符 RATE_COMPUTE_H_
#define RATE_COMPUTE_H_ // 定义标识符 RATE_COMPUTE_H_ ...
float simple_interest(float rate, int day); // 定义函数原型
float compound_interest(float rate, int day);
...
#endif

(3)包含所有利率计算函数定义的头文件 rate_compute.c:

#include "rate_compute.h"		// 包含用户自定义的函数库 rate_compute.h
...
float simple_interest(float rate, int day) // 定义函数
{
... // 定义函数体
} float compound_interest(float rate, int day)
{
...
}
...

这种结构是 C 语言实际开发中经常使用的。主程序文件控制程序主要的流程,而具体功能实现放在其他文件中。与利率计算有关的函数说明放在头文件 rate_compute.h 内,该文件利用编译预处理命令判断自己是否已经被包含,如果没有则进行函数说明。这样可避免因多个文件相互包含时,函数被重复说明而出错。函数定义部分放在头文件配对的 rate_compute.c 文件内,两个文件名前部分相同。rate_compute.c 文件需要使用 #include 语句包含头文件 rate_compute.h,这样,当主程序文件也包含头文件 rate_compute.h,就可以使用这些函数。编译器会处理文件之间的连接问题。

5.6.3 函数库

函数库由一系列函数说明文件和函数定义文件所组成,使用时,将该文件包含在自己的程序文件内。例如需要使用输入输出函数时,可使用标准库内的 stdio.h 文件,需要使用数学函数时,可使用标准库内的 math.h 文件。

Linux 系统上有大量的函数库资源,根据 GPL 协议,这些函数库都能免费使用,并且可按照自己的需求修改。很多Linux 系统上的程序发布时,同时也提供了相应的函数库,以便开发者扩展该程序,或者借助该程序实现程序中某一功能。例如 Pidgin 是 Linux 系统上常用的多协议即时通讯软件,用户可使用 Pidgin 提供的libpurple 开发新的即时通信软件,或者让自己的程序具备即时通信功能。Linux 系统常用的 C 语言函数库如表 9.1 所示。

表 9.1 Linux 系统常用的 C 语言函数库

libdbus D-Bus 进程间通信机制函数库,用于两个应用程序相互联系和交互消息
libpthread POSIX 线程库,用于多线程通信
libthread Solaris 线程库,用于多线程通信
libnet 网络开发库,用于实现和封装了数据包的构造和发送过程
libcurl 客户端 url 传输库,用于数据下载和上传
libpq PostgreSQL 数据库接口,用于操作 PostgreSQL 数据库
GLib GTK+ 和 GNOME 的基础,提供了具备可移植性的数据结构
GTK+ 图形化用户界面构件库,用于开发图形界面
GStreamer GStreamer 多媒体框架函数库,用于开发多媒体播放程序
libgrade Grade 开发库,用于所见即所得方式的图形界面开发

Linux 系统一般将函数放置在 “/lib”和“/usr/lib”两个路径中,GCC 编译器在编译时会自动搜索这两个路径。在位于默认搜索路径之外的函数库,可在环境变量 LD_LIBRARY_PATH 中指明库的搜索路径,或者在“/etc/ld.so.conf”文件中添加库的搜索路径。另外还可以直接将库文件全部复制到程序开发目录中,或者在编译时指定函数库路径。

pkgconfig 程序为配置函数库的路径提供了方便,它用于在编译时指定函数库的路径。

首先需要安装该软件,安装命令如下:

yum install pkgconfig

pkgconfig 可查看已安装的函数库和函数库的版本信息,命令为:

pkg-config --list-all

例如在开发使用 GLib 库的程序时,在编译命令加入参数 “`pkg-config --cflags --libsglib-2.0`”:

gcc -g `pkg-config --cflags --libs glib-2.0` glib_test.c -o glib_test.o

在 Eclipse 中,先用鼠标单击 Project Explorer 中对应的项目名称,选择 Project|Properties 命令打开该项目的属性对话框。然后在对话框左侧的列表框中选择 C/C++Build|Settings 命令打开设置选项卡,在设置选项卡内Tool Settings 列表中选择 GCC C Compiler|Miscellaneous 列表项,将编译参数“`pkg-config --cflags --libs glib-2.0`”加入在 Other flags 文本框原有的内容后。再在同一个列表框中,选择 GCC C Linker|Miscellaneous列表项,将上面的编译参数输入到 Linker flags 文本框原有的内容后。单击 OK 按钮保存。

注意:pkg-config 指令是由一对特殊的符号“`”包围,该符号对应的键盘按键通常位于 Esc键 下方。

【C语言入门教程】5.6 函数库和文件的更多相关文章

  1. Go语言入门教程(十)之函数

    Hello 各位小伙伴大家好,我是小栈君,假期一眨眼就过去了.不知道大家玩的是否开心呢? 上次我们讲到了关于Go语言的流程控制,小栈君也希望小伙伴跟着小栈君一步一个脚印的敲一下代码,相互进步.本期我们 ...

  2. 《JavaScript语言入门教程》记录整理:运算符、语法和标准库

    目录 运算符 算数运算符 比较运算符 布尔运算符 二进制位运算符 void和逗号运算符 运算顺序 语法 数据类型的转换 错误处理机制 编程风格 console对象和控制台 标准库 Object对象 属 ...

  3. 《Ruby语言入门教程v1.0》学习笔记-01

    <Ruby语言入门教程v1.0> 编著:张开川 邮箱:kaichuan_zhang@126.com 想要学习ruby是因为公司的自动化测试使用到了ruby语言,但是公司关于ruby只给了一 ...

  4. 《JavaScript语言入门教程》记录整理:入门和数据类型

    目录 入门篇 js介绍 历史 基本语法 数据类型 概述 null 和 undefined 数值 字符串 对象 函数 数组 本系列基于阮一峰老师的<JavaScrip语言入门教程>或< ...

  5. 《JavaScript语言入门教程》记录整理:面向对象

    目录 面向对象编程 实例对象与 new 命令 this关键字 对象的继承 Object对象的方法 严格模式(strict mode) 本系列基于阮一峰老师的<JavaScrip语言入门教程> ...

  6. Linux pwn入门教程(10)——针对函数重定位流程的几种攻击

    作者:Tangerine@SAINTSEC 本系列的最后一篇 感谢各位看客的支持 感谢原作者的付出一直以来都有读者向笔者咨询教程系列问题,奈何该系列并非笔者所写[笔者仅为代发]且笔者功底薄弱,故无法解 ...

  7. C语言入门教程-(5)格式化输入输出

    1.输入和输出 在程序的使用中,我们经常可以看的这么一个场景:用户需要输入数据,经过程序运算,得到结果后输出.在C语言中,输入数据和输出数据都是由库函数完成的,通过语句来输入/输出. 2.格式化输出— ...

  8. 【C语言入门教程】目录/大纲

    第一章 C语言编程基础 1.1 基本程序结构 1.2 函数库 和 链接 1.3 C语言“32个”关键字 第二章 数据类型.运算符和表达式 2.1 数据类型(5种基本数据类型),聚合类型与修饰符 2.2 ...

  9. 智能合约语言 Solidity 教程系列3 - 函数类型

    Solidity 教程系列第三篇 - Solidity 函数类型介绍. 写在前面 Solidity 是以太坊智能合约编程语言,阅读本文前,你应该对以太坊.智能合约有所了解,如果你还不了解,建议你先看以 ...

  10. c语言该怎么入门?C语言入门教程(非常详细)

    C语言是一门面向过程的编译型语言,它的运行速度极快,仅次于汇编语言.C语言是计算机产业的核心语言,操作系统.硬件驱动.关键组件.数据库等都离不开C语言:不学习C语言,就不能了解计算机底层. 这套「C语 ...

随机推荐

  1. Session对象

    Session对象用于存储在多个页面调用之间特定用户的信息.Session对象只针对单一网站使用者,不同的客户端无法互相访问.Session对象中止于联机机器离线时,也就是当网站使用者关掉浏览器或超过 ...

  2. iOS 简单的动画自定义方法(旋转、移动、闪烁等)

    #define kDegreesToRadian(x) (M_PI * (x) / 180.0) #define kRadianToDegrees(radian) (radian*180.0)/(M_ ...

  3. css3新增属性API

    写在前面:由于CSS5标准还未完全订下来,所以各种内核的浏览器都有自己的标准,为了不使属性混淆,所以各家在各自标准前加了一个前缀. -moz-  主要是firefox火狐 -webikt-主要是chr ...

  4. HD1269迷宫城堡(有向图 && 划分连通块)

    迷宫城堡 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submis ...

  5. python BeautifulSoup4

    source form  http://www.bkjia.com/ASPjc/908009.html 昨天把传说中的BeautifulSoup4装上了,还没有装好的童鞋,请看本人的上一篇博客: Py ...

  6. Ps 技巧

    一.动作(批处理) 二.让图片更清晰 三.标尺 四.画面还原 五.内容识别比例(改变身材) 六.移花接木 七.多人头像 八.多重曝光 九.突出肌肉线条或者脸部轮廓 十.给照片换一个天空 十一.制作光束 ...

  7. BZOJ4690: Never Wait for Weights

    裸带权并查集. #include<cstdio> #define N 100005 int m,i,j,s,t,u,d[N],p[N]; char k; int find(int i){ ...

  8. 签名有元程序集 Signed Friend Assemblies

    下面的例子演示了创建签名程序集和有元程序集.这就要求两个程序集都是强命名,在下面的例子中,两个程序集都用了同一个秘钥,也可以用不同的秘钥. 1. 生成秘钥, 这个在前面的博客中有说明,生成秘钥文件sn ...

  9. 任务二:1、选择器 2、连接集中状态的顺序 3、浮动的用发和原理 4、盒模型在IE和Google等不同浏览器的区别与联系

    1.选择器类型 标签选择器,类选择器,ID选择器,组合选择器,伪类和伪元素,属性选择器,子选择器,同胞选择器, :not()选择器 1.同胞选择器 相邻同胞标签: h2 + p{ color:red; ...

  10. WinForm------RepositoryItemCheckEdit属性介绍

    //去掉第三种状态 editcheck1.OptionView.NullStyle = UnChecked