编译原理---C文件和头文件的关系

简单的说其实要理解C文件与头文件(即.h)有什么不同之处,首先需要弄明白编译器的工作过程;

一般说来编译器会做以下几个过程:

  1. 预处理阶段
  2. 词法与语法分析阶段
  3. 编译阶段,首先编译成纯汇编语句,再将之汇编成跟CPU相关的二进制码,生成各个目标文件 (.obj文件)
  4. 连接阶段,将各个目标文件中的各段代码进行绝对地址定位,生成跟特定平台相关的可执行文件,当然,最后还可以用objcopy生成纯二进制码,也就是去掉了文件格式信息。(生成.exe文件)

编译器在编译时是以C文件为单位进行的,也就是说如果你的项目中一个C文件都没有,那么你的项目将无法编译,连接器是以目标文件(.obj文件)为单位,它将一个或多个目标文件进行函数与变量的重定位,生成最终的可执行文件。

在PC上的程序开发,一般都有一个main函数,这是各个编译器的约定;当然,你如果自己写连接器脚本的话,可以不用main函数作为程序入口!!!!

编译的过程为:(main .c文件 ···>目标文件···>可执行文件 )

有了这些基础知识,再言归正传,为了生成一个最终的可执行文件,就需要一些目标文件,也就是需要C文件,而这些C文件中又需要一个main函数作为可执行程序的入口,那么我们就从一个C文件入手,假定这个C文件内容如下:

//main.c
#include <stdio.h>
#include "mytest.h"
​
int main() 
{ 
    test = 25; 
    printf("test.................%d\n",test);
    return 0;
}

 

头文件内容如下:

//mytest.h
int test;

现在以这个例子来讲解编译器的工作:

  1. 预处理阶段:编译器以C文件作为一 个单元,首先读这个C文件,发现第一句与第二句是包含一个头文件,就会在所有搜索路径中寻找这两个文件;
    补充一个知识点:
    #include <>格式:引用标准库头文件,编译器从标准库目录开始搜索;
    #include ""格式:引用非标准库的头文件,编译器从用户的工作目录开始搜索.
    找到之后,就会将相应头文件中再去处理宏,变量, 函数声明,嵌套的头文件包含等,检测依赖关系,进行宏替换,看是否有重复定义与声明的情况发生,最后将那些文件中所有的东东全部扫描进这个当前的C文件 中,形成一个中间“C文件”;
  2. 编译阶段 :在上一步中相当于将那个头文件中的test变量扫描进了一个中间C文件,那么test变量就变成了这个文件中的一个全局变量,此时就将所有这个中间C文件的所有变量,函数分配空间,将各个函数编译成二进制码,按照特 定目标文件格式生成目标文件,在这种格式的目标文件中进行各个全局变量,函数的符号描述,将这些二进制码按照一定的标准组织成一个目标文件;
  3. 连接阶段 :将上一步成生的各个目标文件,根据一些参数,连接生成最终的可 执行文件,主要的工作就是重定位各个目标文件的函数
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值