一文搞懂C/C++常用编译器
1. C++ 编译器介绍
MSVC,GCC和Clang是业界三种最主流的C/C++编译器,下面粗劣比较一下他们的差异:
C++编译器 | 编译器全称 | 支持的平台 | 备注 |
---|---|---|---|
MSVC | Microsoft Visual C++ | Windows | 由微软开发,主要用于Windows平台应用程序的开发。Visual Studio系列IDE默认集成了该编译器 |
GCC | GNU Compiler Collection | Windows, Linux, macOS | 开源编译器,支持多种平台,Linux下C++开发一般默认会使用此编译器 |
Clang | Clang / Low Level Virtual Machine | Windows, Linux, macOS | LLVM项目的一部分,提供高效的编译性能。macOS的XCode工具默认集成了此编译器 |
1.1. MSVC
- MSVC(Microsoft Visual C++)由微软开发,主要用于Windows平台应用程序的开发。
- Visual Studio系列IDE默认集成了该编译器,可以通过下载安装Visual Studio安装包来安装。
- MSVC只能在Windows下用,不支持跨平台。
1.1.1. Visual C++
与Visual Studio
的版本对应关系
_MSC_VER
: 是MSVC编译器内置的宏定义,可以在源代码中直接引用。其值代表了MSVC编译器的版本,如:1900表示Visual Studio 2015(MSVC++ 14.0)。
MSC 1.0 _MSC_VER == 100
MSC 2.0 _MSC_VER == 200
MSC 3.0 _MSC_VER == 300
MSC 4.0 _MSC_VER == 400
MSC 5.0 _MSC_VER == 500
MSC 6.0 _MSC_VER == 600
MSC 7.0 _MSC_VER == 700
MSVC++ 1.0 _MSC_VER == 800
MSVC++ 2.0 _MSC_VER == 900
MSVC++ 4.0 _MSC_VER == 1000 (Developer Studio 4.0)
MSVC++ 4.2 _MSC_VER == 1020 (Developer Studio 4.2)
MSVC++ 5.0 _MSC_VER == 1100 (Visual Studio 97 version 5.0)
MSVC++ 6.0 _MSC_VER == 1200 (Visual Studio 6.0 version 6.0)
MSVC++ 7.0 _MSC_VER == 1300 (Visual Studio .NET 2002 version 7.0)
MSVC++ 7.1 _MSC_VER == 1310 (Visual Studio .NET 2003 version 7.1)
MSVC++ 8.0 _MSC_VER == 1400 (Visual Studio 2005 version 8.0)
MSVC++ 9.0 _MSC_VER == 1500 (Visual Studio 2008 version 9.0)
MSVC++ 10.0 _MSC_VER == 1600 (Visual Studio 2010 version 10.0)
MSVC++ 11.0 _MSC_VER == 1700 (Visual Studio 2012 version 11.0)
MSVC++ 12.0 _MSC_VER == 1800 (Visual Studio 2013 version 12.0)
MSVC++ 14.0 _MSC_VER == 1900 (Visual Studio 2015 version 14.0)
MSVC++ 14.1 _MSC_VER == 1910 (Visual Studio 2017 version 15.0)
MSVC++ 14.11 _MSC_VER == 1911 (Visual Studio 2017 version 15.3)
MSVC++ 14.12 _MSC_VER == 1912 (Visual Studio 2017 version 15.5)
MSVC++ 14.13 _MSC_VER == 1913 (Visual Studio 2017 version 15.6)
MSVC++ 14.14 _MSC_VER == 1914 (Visual Studio 2017 version 15.7)
MSVC++ 14.15 _MSC_VER == 1915 (Visual Studio 2017 version 15.8)
MSVC++ 14.16 _MSC_VER == 1916 (Visual Studio 2017 version 15.9)
MSVC++ 14.2 _MSC_VER == 1920 (Visual Studio 2019 Version 16.0)
MSVC++ 14.21 _MSC_VER == 1921 (Visual Studio 2019 Version 16.1)
MSVC++ 14.22 _MSC_VER == 1922 (Visual Studio 2019 Version 16.2)
MSVC++ 14.30 _MSC_VER == 1930 (Visual Studio 2022 Version 17.0)
MSVC++ 14.31 _MSC_VER == 1931 (Visual Studio 2022 Version 17.1)
1.1.2. 工具链的主要工具
工具 | 功能描述 |
---|---|
cl.exe | 编译程序 |
link.exe | 链接程序 |
lib.exe | 加载lib库的程序 |
nmake.exe | 用makefile进行构建、编译的工具 |
备注: 用户只需要调用cl.exe,即可完成编译-链接全过程。因为cl.exe程序在编译时自己会去调用link.exe、lib.exe等程序。
1.2. GCC
GCC
最开始的原名是GNU C Compiler
,是GNU项目的C语言编译器。后来逐步拓展支持了更多的语言,支持编译C、C++、Fortran、Pascal、Objective-C、Java、Ada、Go等,所以变成了GNU Compiler Collection
(GNU编译器套装),是一套由GNU项目开发的支持多种编程语言的编译器工具链。
GCC支持多种平台和操作系统,包括Linux、Windows、macOS等,并且是许多开源项目和操作系统的标准编译器,如Linux内核。GCC还支持多种CPU指令集架构,如:X86、ARM等。
1.2.1. GCC的主要优点
- 支持多语言: 支持多种编程语言,如C、C++、Fortran、Pascal、Objective-C、Java、Ada、Go等。
- 跨平台性: GCC编译器能够在不同的操作系统和硬件平台上编译和运行代码,确保了代码的高度可移植性。
- 性能优化: GCC编译器内置了多种优化策略,可以根据不同的编译选项进行代码优化,从而提升程序的运行效率。
- 功能丰富: 编译时可生成调试信息,便于开发者进行调试。并提供了广泛的编译选项和扩展功能,以满足不同开发者的需求。
1.2.2. GCC的常用工具
工具 | 描述 |
---|---|
gcc | GCC的主要编译器,用于将源代码编译为可执行文件或库。支持多种语言(如C、C++、Fortran等),并提供丰富的编译选项。 |
g++ | GCC的C++编译器,用于将C++源代码编译为可执行文件或库。与gcc共享许多相同的编译选项,同时支持针对C++的特定选项。 |
gdb | GCC附带的调试器,用于调试程序。允许在程序运行时设置断点、单步执行代码、查看变量值等。支持多种编程语言,提供强大的调试功能。 |
objdump | 用于反汇编目标文件或可执行文件,显示二进制文件的汇编代码。还可显示符号表信息、重定位表等相关信息。 |
nm | 用于列出目标文件或可执行文件中的符号表。显示函数、变量以及其他符号的名称和地址。 |
ar | 用于创建、修改和提取静态库文件。允许将多个目标文件打包成一个库文件,以便在编译时链接使用。 |
size | 用于查看目标文件或可执行文件的大小信息。显示代码段、数据段和符号表等各部分的大小统计。 |
readelf | 用于显示ELF(Executable and Linkable Format)格式的二进制文件的详细信息。显示段表、符号表、动态链接信息等。 |
1.2.3. MinGW
MinGW(Minimalist GNU for Windows)是一个用于Windows平台的开发环境,它提供了GNU编译器集合(GCC)的Windows版本。MinGW允许开发者在Windows上使用GCC编译器来编译C、C++和其他支持的语言。MinGw只支持32位Widnows系统,MinGW-w64 支持32位和64位。所以现在说MinGW时,一般默认指的MinGW-w64,见 MinGW官网。
主要特点:
- GCC编译器: MinGW包含了GCC编译器,支持C、C++、Fortran等语言。
- 跨平台开发: 开发者可以使用MinGW编译的程序在Windows上运行,同时保持与Linux和其他Unix-like系统的兼容性。
- 开源: MinGW是开源的,遵循GNU通用公共许可证(GPL)。
- 轻量级: MinGW提供了一个轻量级的开发环境,不需要复杂的安装和配置。
1.3. Clang/LLVM
1.3.1. Clang介绍
Clang
是一个由 LLVM 项目开发的 C、C++、Objective-C 等编程语言的编译器前端。它旨在提供更快的编译速度、更好的错误报告及与GCC兼容的编译器驱动程序。Clang 是 LLVM 编译器基础设施的一部分,通常与 LLVM 后端一起使用来生成机器代码。
Clang的主要特点包括:
- 快速编译和低内存使用: Clang 的设计目标之一是提供比 GCC 更快的编译速度和更低的内存占用。
- 高质量的错误和警告信息: Clang 提供了详细和易于理解的错误和警告信息,有助于开发者更快地找到和修复问题。
- 与 GCC 兼容: Clang 支持大多数 GCC 的编译器选项和工具链,使得从 GCC 迁移到 Clang 相对容易。
- 模块化设计: Clang 的架构是模块化的,易于扩展和集成到其他工具和流程中。
- 支持现代语言特性: Clang 支持最新的 C++ 标准和其他语言特性,使得开发者可以使用最新的编程技术。
Clang 不仅是一个编译器前端,还是一个强大的工具集,包括静态分析工具(clang-tidy)、代码格式化工具(clang-format)、重构工具等,这些工具可以帮助开发者提高代码质量和开发效率。
1.3.2. Clang与LLVM的关系
编译器的组成:
一个完整的编译器通常由三部分组成。
前端(FrontEnd): 主要负责词法和语法分析,将源代码转化为抽象语法树;
优化器(Optimizer): 则是在前端的基础上,对得到的中间代码进行优化,使代码更加高效;
后端(BackEnd): 后端则是将已经优化的中间代码转化为针对各自平台的机器代码。
Clang与LLVM的关系:
更粗粒度的划分是把优化器
和后端
统称为后端
,整个编译器就由前端和后端两部分组成。Clang就是编译器的前端,负责词法和语法分析;LLVM就是编译器的后端,负责优化和生成机器代码。
Clang/llvm的编译过程如下图:
LLVM 包括了两个概念:
- 广义的 LLVM: 指的是一个完整的 LLVM 编译器框架系统,包括了前端、优化器、后端、众多的库函数以及很多的模块。
- 狭义的 LLVM: 则是聚焦于编译器后端功能的一系列模块和库,包括代码优化、代码生成、JIT 等。
1.3.3. Clang/LLVM与GCC
GCC和LLVM是竞争对手,都是编译器框架系统。GCC包含前端和后端,LLVM也包含前端和后端,只是他的前端通常是Clang,所以Clang是LLVM 编译器框架系统 的前端。
他们可能的组合如下:
眼尖的同学可能会问:为什么没有“Clang前端、GCC后端”的组合?
个人理解: GCC发展的时间非常早,带有很大的历史包袱。GCC后端的接口设计没有那么灵活,不能提供Clang足够的接口支撑(这也是LLVM架构最开始设计就考虑到的问题)。
LLVM Compiler
发展过程的早期就经历了LLVM-GCC
这种过渡期的组合(GCC前端+LLVM后端)。
2. C++ 编译器的安装
2.1. Windows
2.1.1. MSVC安装
- 进入微软官网下载页面:https://visualstudio.microsoft.com/zh-hans/downloads/
- 选择要下载的最新版本安装包下载器:
- 如果要下载完整的Visual Studio IDE,选择:Visual Studio 2022 -> 版本类型(如果是个人开发使用,可以选择
Visual Studio Community 2022
) - 如果只需要下载MSVC编译器,选择: 用于Visual Studio的工具 -> Visual Studio 2022 生成工具。
- 我希望用VSCode(而不是Visual Studio)来开发C++, 所有我只需要下载MSVC编译器。
- 如果要下载完整的Visual Studio IDE,选择:Visual Studio 2022 -> 版本类型(如果是个人开发使用,可以选择
- 双击打开下载好的
vs_BuildTools.exe
,一路点击“继续”,到安装包选择页面时,选择“C++桌面开发”。
2.1.2. 环境变量配置
方法一 指定的命令行:
MSVC安装后会生成特定命令行工具,可以在“开始 -> 搜索”查找一下命令行:
Developer Command Prompt for VS 2022
: 用 32位x86编译器 构建 32位x86 的目标程序。x86 Native Tools Command Prompt for VS 2022
: 用 32位x86编译器 构建 32位x86 的目标程序。x64 Native Tools Command Prompt for VS 2022
: 用 64位x64编译器 构建 64位x64 的目标程序。x86_x64 Cross Tools Command Prompt for VS 2022
: 用 86位x32编译器 构建 64位x64 的目标程序。x64_x86 Cross Tools Command Prompt for VS 2022
: 用 64位x64编译器 构建 32位x86 的目标程序。
打开对于的命令行,然后在此命令行下执行cl xx.cpp
等相关编译命令。
方法二 bat脚本设置:
C:\software\MicrosoftVisualStudio\2022\BuildTools\VC\Auxiliary\Build
下存在多个批处理文件,这些批处理文件可以初始化相应构建需求的环境变量:
vcvars32.bat
: 使用 32位x86 编译器构建 32位x86 代码。vcvars64.bat
: 使用 64位x64 编译器构建 64位x64 代码。vcvarsx86_amd64.bat
: 使用 32位x86 本机兼容工具生成 64位x64 代码。vcvarsamd64_x86.bat
: 使用 64位x64 本机兼容工具生成 32位x86 代码。vcvarsx86_arm.bat
: 使用 32位x86 本机兼容工具生成 ARM 代码。vcvarsamd64_arm.bat
: 使用 64位x64 本机兼容工具生成 ARM 代码。vcvarsx86_arm64.bat
: 使用 32位x86 本机兼容工具生成 ARM64 代码。vcvarsamd64_arm64.bat
: 使用 64位x64 本机兼容工具生成 ARM64 代码。
打开cmd命令行
或者power shell
, 然后执行相应的.bat
脚本然,再执行cl xx.cpp
等相关编译命令。
方法三 手动配置:
MSVC编辑器的默认安装在C:\Program Files (x86)\Microsoft Visual Studio
,安装时可以自定义安装路径。在安装目录下的2022\BuildTools\VC\Tools\MSVC\14.40.33807\bin
路径下,其中有两个文件夹,分别是hostx64和hostx86,这两个文件夹下又分别有x64和x86,他们的含义如下:
bin
Hostx64 # 主机是64位的编译器
x64 # 编译的目标文件是64位程序
x86 # 编译的目标文件是32位程序
Hostx86 # 主机是32位的编译器
x64 # 编译的目标文件是64位程序
x86 # 编译的目标文件是32位程序
根据自己的需求,选择对应的路径,如:我的主机是64位的,我希望用64位的编译器编译32位的目标程序,设置环境变量如下:
MSVC_DIR: C:\software\MicrosoftVisualStudio\2022\BuildTools\VC\Tools\MSVC\14.40.33807
include: %MSVC_DIR%\include
lib: %MSVC_DIR%\lib\x86;
path: %MSVC_DIR%\bin\Hostx64\x86;
2.2. Linux(Ubuntu)
2.2.1. 安装GCC/GDB
1. 安装:
# 更新软件源
sudo apt update
# 通过以下命令安装编译器和调试器
sudo apt install build-essential gdb
Ubuntu 默认情况下没有提供C/C++编译环境的,你可以单独安装gcc、g++等工具,但会比较麻烦。Ubuntu提供了一个build-essential软件包,安装了该软件包,编译c/c++所需要的软件包也都会被安装。
2. 校验:
# 执行以下命令确认每个软件是否安装成功
# 如果成功,则显示版本号
gcc --version
g++ --version
gdb --version
2.2.2. 安装CMake
1. 安装:
sudo apt install cmake
1. 校验:
cmake --version
2.3. macOS
2.3.1. clang的安装
macOS下,我们可以通过安装Xcode命令行工具
来安装clang,因为Xcode命令行工具
中包含了clang。
-
在命令行中输入
xcode-select --install
,之后你会看到一个面板,要求你安装 Xcode 命令行工具。
-
点击 “Install”(安装),开始下载和安装过程。
-
当安装完成后,你会看到一个确认信息。
-
验证 XCode 是否安装成功
输入xcode-select -p
,如果看到下面的内容说明安装成功:/Library/Developer/CommandLineTools
-
验证 Clang 是否安装成功
输入clang --version
,如果看到下面的内容,说明安装成功:Apple Clang version 15.0.0 (Clang-1500.3.9.4) Target: x86_64-apple-darwin23.5.0 Thread model: posix InstalledDir: /Library/Developer/CommandLineTools/usr/bin
2.3.2. 为什么gcc的版本号显示的是Clang version
?
Xcode命令行工具
安装完后,就已经包含gcc/g++工具了,我们可以查看一下其版本号
➜ ~ gcc --version
Apple Clang version 15.0.0 (Clang-1500.3.9.4)
Target: x86_64-apple-darwin23.5.0
Thread model: posix
InstalledDir: /Library/Developer/CommandLineTools/usr/bin
➜ ~ g++ --version
Apple Clang version 15.0.0 (Clang-1500.3.9.4)
Target: x86_64-apple-darwin23.5.0
Thread model: posix
InstalledDir: /Library/Developer/CommandLineTools/usr/bin
你有没有发现一个奇怪的现象:我们要查看的是gcc/g++的版本号,这里显示的版本号为什么是Apple Clang version XXX
?
个人的理解: 这里的gcc/g++已经不是GNU Compiler Collection
中的gcc/g++了, 某种意义上讲,他可能是 Clang/clang++ 的一个别名,底层的实现可能都换了,只是在接口上他做到了与GCC兼容。因为 Clang 设计的初衷就是为了超越和取代GCC的。
2.3.3. gcc的安装
如果你想独立安装GNU Compiler Collection
,而不是XCode自带的gcc/g++,要如何操作?
- 用homebrew安装gcc(如果homebrew未安装请自行安装,这里不再讲解homebrew的安装方法)。
brew install gcc
- 安装完后,找到上述命令安装的GCC版本
➜ ~ ls -l /usr/local/bin | grep g++
lrwxr-xr-x 1 spencer admin 33 8 2 17:08 g++-14 -> ../Cellar/gcc/14.1.0_2/bin/g++-14
lrwxr-xr-x 1 spencer admin 55 8 2 17:08 x86_64-apple-darwin23-g++-14 -> ../Cellar/gcc/14.1.0_2/bin/x86_64-apple-darwin23-g++-14
➜ ~
➜ ~ g++-14 --version
g++-14 (Homebrew GCC 14.1.0_2) 14.1.0
Copyright (C) 2024 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
说明我们的GCC安装成功,安装的版本是:14.1.0。可以用同样的方式查找gcc。
- 修改配置
在~/.bash_profile
文件添加如下内容:
alias gcc='gcc-14'
alias cc='gcc-14'
alias g++='g++-14'
alias c++='c++-14'
如果你用的是zsh,则在~/.zshrc
文件中添加。
- 加载配置
# bash
source ~/.bash_profile
# zsh
source ~/.zshrc
- 再次验证版本号
➜ ~ gcc --version
gcc-14 (Homebrew GCC 14.1.0_2) 14.1.0
Copyright (C) 2024 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
➜ ~ g++ --version
g++-14 (Homebrew GCC 14.1.0_2) 14.1.0
Copyright (C) 2024 Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
可以看到现在版本号不再显示Apple Clang version XXX
了。
3. 验证编译器是否安装正常
3.1. 写一个测试Demo
- 创建一个目录,如
test_demo
,并进入该目录。 - 在该目录下创建一个
test.cpp
文件,并输入以下代码:
#include <iostream>
int main()
{
std::cout << "Hello, world!" << std::endl;
return 0;
}
3.2. 编译并运行
3.2.1. Windows
cl test.cpp
test.exe
3.2.2. Linux
g++ test.cpp
./a.out
3.2.3. macOS
clang++ test.cpp
./a.out
如何有正常输出Hello, world!
则说明编译器安装成功。
大家好,我是陌尘。
IT从业10年+, 北漂过也深漂过,目前暂定居于杭州,未来不知还会飘向何方。
搞了8年C++,也干过2年前端;用Python写过书,也玩过一点PHP,未来还会折腾更多东西,不死不休。
感谢大家的关注,欢迎加我微信(Spencer_MC),期待与大家一起交流。