xx.h和xx.c的奥妙

 

xx.hxx.c的奥妙

示例代码:

/********************* A.h*********************/

#ifndef __A_H__

#define __A_H__

 

void fun();
 

#endif

 

 

/********************* A.c*********************/

#include "a.h"    //为什么要加?
void fun()
{
    return;
}

 

/******************** main.c********************/

#include "a.h"
int main( )
{
fun(); 
return 0;
}

 

为什么经常见xx.c里面include对应的xx.hA.c中的#include "A.h"是否多余?
主要有两种原因:

如果.c中的函数也需要调用同个.c中的其他函数,那么这个.c往往会include同名的.h,避免声明和调用顺序出现问题(C语言要求使用之前必须声明,而include同名.h一般会放在.c的开头)。

.c中的函数中经常会使用了同名.h文件定义的宏,或者typedef定义的新类型。

有很多工程甚至把这种写法约定为代码规范,以规范出清晰的代码来。

由此,有很多工程甚至把这种写法约定为代码规范,以规范出清晰的代码来。以上示例中,显示是可有可无的。

C编译器角度看,.h.c只是后缀符号,毫无意义。换句话说,就是.h.c没有必然联系。

1.预处理

预处理只是简单的替换,#include "xx.h"中所包含的完全展开到包含它的.c 文件中。.h只起到这个作用。

2.编译过程

以一个文件为基本的一个编译单元。一个.c文件生成一个.o文件,在编译阶段,只要.c或者包含的.h中已经声明的函数或变量,.c都会生成相应的.o文件。编译阶段对函数或变量的定义并无要求,所以在main.c中,即便void fun()是在A.c中定义的,但其包含的头文件中已经声明,即可顺利编译。

 

3.连接过程

A.omain.o结合起来,生成可执行文件。

若只是声明,没有在其他的.c中定义,连接时就会出错。也就是说若void fun()没有在A.c中定义,连接就会出错。不管是函数还是变量都是同样的道理。

随便提一下:若只是声明,而未定义。但是其声明的函数或变量并未使用,也是可以的连接通过的。

 

 

 

总结一下,.h一般放的是同名.c文件中定义的变量、数组、函数的声明,需要让.c外部使用的声明。这个声明有啥用?只是让需要用这些声明的地方方便引用。因为#include "xx.h"这个宏其实际意思就是把当前这一行删掉,把xx.h中的内容原封不动的插入在当前行的位置。只是一个简单的代码替换。由于想写这些函数声明的地方非常多(每一个调用xx.c中函数的地方,都要在使用前声明一下子),所以用#include "xx.h"这个宏就简化了许多行代码——让预处理器自己替换好了。也就是说,xx.h其实只是让需要写xx.c中函数声明的地方调用,至于include这个.h文件是谁,是.h还是.c,还是与这个.h同名的.c,都没有任何必然关系。

只要想调用xx.c中的某个函数,就直接包含includexx.h,宏替换后也可能会出现了很多无用的声明,不过这样整个版面很清晰。多些声明(.h一般只用来放声明,而放不定义)没有任何坏处,不会影响编译。

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值