【C/C++】程序的构建(编译)过程概述

🦄个人主页:小米里的大麦-CSDN博客

🎏所属专栏:C++_小米里的大麦的博客-CSDN博客

🎁代码托管:C++: 探索C++编程精髓,打造高效代码仓库 (gitee.com)

⚙️操作环境:Visual Studio 2022

目录

一、前言

二、预处理(Preprocessing)

三、编译(Compilation)

四、汇编(Assembly)

五、链接(Linking)

总结 

各阶段输出总结

流程总结

共勉


一、前言

每个语言和环境都有其特定的构建和执行流程,但大多数都会涉及某种形式的处理,将源代码转换成机器可以直接理解的形式。在编译和构建一个 C/C++ 程序的过程中,通常会经过 预处理编译汇编链接 这四个阶段,这个过程被称为构建流程或者编译流程。每个阶段都负责将代码从一个形式转换为下一个形式,最终生成可执行文件。下面我会以一个简单的C/C++程序详细讲解每个阶段的具体过程。

注意:编译器的工作其实非常复杂,远远不是博主我这轻描淡写的两句话就能描述清楚的!想要深入了解,还需不断钻研!!!

二、预处理(Preprocessing)

预处理阶段是编译过程的第一个步骤,主要负责对代码进行宏替换、头文件展开、条件编译等操作。这一阶段的任务是将代码进行格式化标准化,方便后续的编译步骤。

  • 头文件展开#include 指令引入的头文件会被展开,将头文件中的内容插入到文件中。
  • 宏替换:预处理阶段会替换所有的宏定义,例如 #define MAX 100,在代码中使用 MAX 的地方都会被替换为 100
  • 条件编译:根据 #ifdef#ifndef 等预处理指令,编译器会有选择地包含或忽略某些代码。
  • 删除注释:所有的代码注释(///* ... */)会在预处理阶段被移除,代码中只会保留实际的指令。

输出:经过预处理的源文件会生成一个新的文件,通常扩展名为 .i,这就是纯净的、展开后的源代码文件。

例如:

#include <stdio.h>
#define PI 3.14
int main() {
    printf("%f\n", PI);//打印PI的值
}

预处理后:

int main() {
    printf("%f\n", 3.14);
}

三、编译(Compilation)

编译器会将预处理后的源代码(.i 文件)转化为汇编代码。这一阶段会对代码的语法进行检查,确保没有语法错误,并且会生成与硬件无关的汇编语言代码。

  • 语法分析:编译器会检查代码的语法,确保代码符合 C/C++ 语言规范。如果语法有问题,编译器会抛出错误。
  • 语义分析:编译器会检查变量类型、函数调用等,确保它们的使用是正确的。
  • 生成汇编代码:编译器会将源代码转换成一种与 CPU 架构无关的汇编代码。这个文件通常以 .s 作为后缀。

输出:经过编译后的文件通常以 .s 为后缀,它包含的是汇编代码。

例子(生成的汇编代码部分,大致是这样,会有部分不准确):

movl $0, %eax
call printf

四、汇编(Assembly)

在汇编阶段,汇编器会将汇编代码(.s 文件)转换成机器代码(即二进制指令)。这些二进制指令可以直接被计算机的处理器执行。

  • 汇编器会将汇编语言翻译成机器指令,这些指令以二进制格式存储在目标文件(.o.obj)中。
  • 目标文件是不可执行的,它只是包含了机器代码和一些符号信息(如变量、函数名等),供下一步的链接使用。

输出:这个阶段的输出是一个目标文件,通常以 .o.obj 作为后缀,里面包含了二进制机器代码。

五、链接(Linking)

链接是编译过程的最后一步,负责将一个或多个目标文件(.o 文件)合并,生成一个可执行文件。这个阶段包括以下几项工作:

  • 符号解析:链接器会解析每个目标文件中的符号(如函数和变量),并将它们正确地关联在一起。比如,如果一个目标文件调用了一个在另一个目标文件中定义的函数,链接器会负责将它们连接起来。
  • 库链接:链接器会将程序需要的库文件(如标准库 libc)与目标文件链接在一起,确保程序能调用库函数。
  • 地址分配:链接器会为每个符号(函数、变量)分配内存地址,使得程序在执行时可以正确访问它们。

输出:链接后的最终产物是一个可执行文件,通常命名为 a.out(在 Linux/Unix 系统中)或 .exe 文件(在 Windows 系统中)。

例子:链接后,生成的可执行文件可以直接运行,执行程序逻辑。

下面放几张图片使抽象的理解形象些:

 

总结 

各阶段输出总结

  • 预处理(Preprocessing):生成预处理后的源代码文件,通常扩展名为 .i
  • 编译(Compilation):生成汇编代码文件,通常扩展名为 .s
  • 汇编(Assembly):生成目标文件,通常扩展名为 .o.obj
  • 链接(Linking):生成可执行文件,扩展名为 a.out(Linux/Unix)或 .exe(Windows)。

流程总结

  1. 预处理:对代码做初步的处理,如头文件展开、宏替换等。
  2. 编译:将预处理后的代码转化为汇编代码,同时进行语法检查。
  3. 汇编:将汇编代码转换为机器代码,生成目标文件。
  4. 链接:将目标文件与库文件链接,生成可执行程序。

这个编译过程将源代码逐步转化为计算机可以执行的二进制机器代码,是 C/C++ 编译过程的核心。

共勉

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/878866.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

C# USB通信技术(通过LibUsbDotNet库)

文章目录 1.下载LibusbDotNet库2.引入命名空间3. 实例化USB设备4.发送数据5.关闭连接 1.下载LibusbDotNet库 右击项目选择管理NuGet程序包在弹出的界面中搜索LibusbDotNet&#xff0c;然后下载安装。 2.引入命名空间 using LibUsbDotNet; using LibUsbDotNet.Main;3. 实例化…

MoneyPrinterTurbo 安装使用流程

项目地址&#xff1a; https://github.com/harry0703/MoneyPrinterTurbo 开发环境&#xff1a;mac 1 git 下载 # 下载代码到本地 git clone https://github.com/harry0703/MoneyPrinterTurbo.git cd MoneyPrinterTurbo2 docker 配源 在 docker 安装目录执行以下命令显示隐藏…

《Nginx核心技术》第17章:使用自签CA配置HTTPS加密反向代理访问

作者&#xff1a;冰河 星球&#xff1a;http://m6z.cn/6aeFbs 博客&#xff1a;https://binghe.gitcode.host 文章汇总&#xff1a;https://binghe.gitcode.host/md/all/all.html 星球项目地址&#xff1a;https://binghe.gitcode.host/md/zsxq/introduce.html 沉淀&#xff0c…

3.Java高级编程实用类介绍(一)

三、Java高级编程实用类介绍(一) 文章目录 三、Java高级编程实用类介绍(一)一、枚举类型二、包装类三、Math 一、枚举类型 使用enum进行定义 public enum 枚举名字{值1,值2.... }二、包装类 每个基本类型在java.lang包中都有一个相应的包装类 /** new包装类&#xff08;字符…

华硕产品资料的查询方法

华硕网站有些奇怪&#xff0c;比如我要查询x99-pro这款已经停售的主板的资料&#xff0c;在它的首页搜索&#xff0c;搜索结果为空&#xff1a; 然后在服务支持和下载中心&#xff0c;同样搜不到。 经高人指点&#xff0c;用下面的方法&#xff0c;可以搜到&#xff1a; https…

C++ char*和char[] 可能指向的内存区域详解(附实验)

C char* 指向的内存区域详解 写在前面c内存结构简介指针常量和常量指针简介情况一&#xff1a;char* 指向栈区内容情况二&#xff1a;char* 指向堆区内容情况三&#xff1a;char* 指向常量区内容情况四&#xff1a;char* 指向静态区内容情况五&#xff1a;char* 指向全局区内容…

mysql 8.0 时间维度表生成(可运行)

文章目录 mysql 8.0 时间维度表生成实例时间维度表的作用时间维度表生成技术细节使用时间维度表的好处 mysql 8.0 时间维度表生成实例 时间维度表的作用 dim_times&#xff08;时间维度表&#xff09;在数据仓库&#xff08;Data Warehouse&#xff09;中的作用至关重要。作为…

Vite + Electron 时,Electron 渲染空白,静态资源加载错误等问题解决

问题 如果在 electron 里直接引入 vite 打包后的东西&#xff0c;那么有些资源是请求不到的 这是我的引入方式 根据报错&#xff0c;我们来到 vite 打包后的路径看一看 &#xff0c;修改一下 dist 里的文件路径试了一试 修改后的样子&#xff0c;发现是可以的了 原因分析 …

Java-idea小锤子图标

这一版的idea小锤子图标其实就在这里 点进去就找到了~

航空航司reese84逆向

reese84逆向 Reese84 是一种用于保护网站防止自动化爬虫抓取的防护机制&#xff0c;尤其是在航空公司网站等需要严格保护数据的平台上广泛使用。这种机制通过复杂的指纹识别和行为分析技术来检测和阻止非人类的互动。例如&#xff0c;Reese84 可以通过分析访问者的浏览器指纹、…

java技术栈介绍

Java技术栈是一个庞大而丰富的生态系统&#xff0c;它包含了从基础语言特性到高级框架、库和工具的整个集合。这个技术栈为开发者提供了构建各种类型应用&#xff08;包括企业级应用、Web应用、移动应用、大数据应用等&#xff09;所需的全部组件。以下是对Java技术栈的一个更详…

Java 技巧 如何在IDEA2024 中快速打出System.out.println();

1.基本用法 键入sout回车 回车后变成&#xff1a; 2.打印变量 快速打印变量,以打印变量名为set为例&#xff0c;set.sout回车&#xff0c; 回车后变成

YOLOv8 人体姿态估计动作识别关键点检测(代码+教程)

YOLOv8 人体姿态判断 项目介绍 YOLOv8 人体姿态判断 是一个基于最新YOLOv8模型的深度学习项目&#xff0c;旨在识别和分析人体姿态。该项目利用先进的计算机视觉技术和深度学习框架&#xff0c;通过摄像头捕捉实时图像或处理存储图像&#xff0c;识别人体的关键点&#xff0c…

ubuntu服务器版NVIDIA驱动失效解决方案

ubuntu服务器版NVIDIA驱动失效解决方案 1. 问题描述2. 解决方法--卸载并重新安装最新版显卡驱动cudacudnn2.1 卸载显卡驱动2.2 重新安装最新版显卡驱动cudacudnn2.2.1 显卡驱动2.2.2 cuda2.2.3 cuda安装cudnn 1. 问题描述 在终端输入nvidia-smi&#xff0c;输出如下&#xff1…

安全工具 | 使用Burp Suite的10个小tips

Burp Suite 应用程序中有用功能的集合 img Burp Suite 是一款出色的分析工具&#xff0c;用于测试 Web 应用程序和系统的安全漏洞。它有很多很棒的功能可以在渗透测试中使用。您使用它的次数越多&#xff0c;您就越发现它的便利功能。 本文内容是我在测试期间学到并经常的主要…

oracle 使用 PL/SQL Developer创建表并插入单条、多条数据

第一步&#xff1a;使用工具创建表&#xff08;前提是库已经创建好了&#xff09;&#xff1a;在当前用户下找到Tables 然后点击并右键&#xff0c;点击新建 写上表名&#xff0c;写上表名的注释 第二步添加字段&#xff1a;点击列&#xff0c;然后分别写上你自己需要的字段及名…

在线查看 Android 系统源代码 AOSPXRef and AndroidXRef

在线查看 Android 系统源代码 AOSPXRef and AndroidXRef 1. AOSPXRef1.1. http://aospxref.com/android-14.0.0_r2/1.2. build/envsetup.sh 2. AndroidXRef2.1. http://androidxref.com/9.0.0_r3/2.2. build/envsetup.sh 3. HELLO AndroidReferences 1. AOSPXRef http://aospx…

QT项目添加资源文件

效果 1.先将图片等资源文件复制到QT项目源码目录中。 2.再添加资源文件 打开资源文件编辑 全选文件 代码

Leetcode—740. 删除并获得点数【中等】(unordered_map+set+sort)

2024每日刷题&#xff08;162&#xff09; Leetcode—740. 删除并获得点数 算法思想 实现代码 class Solution { public:int deleteAndEarn(vector<int>& nums) {unordered_map<int, int> freq;set<int> st;sort(nums.begin(), nums.end());int n num…

MySQL —— 视图

概念 视图是一张虚拟的表&#xff0c;它是基于一个或多个基本表或其他视图的查询结果集。 视图本身不存储数据&#xff0c;而是通过执行查询来动态生成数据&#xff0c;用户可以像操作普通表一样使用视图来进行查询更新与管理等操作。 视图本身也不占用物理存储空间&#xf…