(二)建立项目
项目结构
如果没有构建系统,项目不过是文件的集合,CMake 使用 CMakeLists.txt 定义可以构建的内容及其构建方式、可运行的测试以及要创建的包。
CMake 会读取该文件并生成针对不同平台的构建工具的项目文件。
作为基础,CMake 认为项目至少包含两个目录:源文件目录和二进制文件目录。源文件目录是CMakeLists.txt 和源代码文件及其他构建过程所需的文件存在位置。源文件目录通常由类似 Git 这种版本控制工具来管理。
二进制目录是构建过程中产生的。该目录也经常被叫做构建目录,这种叫法更合乎习惯。CMake 和选定的构建工具(make,Visual Studio等)以及 CTest,CPack 会在构建目录中创建各种文件和子目录,包括可执行文件、库、测试输出文件、包,以及 Makefiles、XCode、Visual Studio的工程文件等。CMake 也会在该目录中创建 CMakeCache.txt 文件以供后续重复利用。
CMakeLists.txt 文件是项目的标准描述文件,所生成的项目文件应被视为构建输出的一部分。
当开始一个新项目时,首选要决定的就是构建目录与源目录之间的相对位置关系。大体上有两种方案:in-source 和 out-of-source 构建。
in-source
指将源文件和构建过程产生的文件放在同一目录,虽然可行但不鼓励。这种方案不适于管理,尤其是不适合使用版本控制工具。
out-of-source
这种方案不仅规避了 in-source 中的问题,还允许创建多个构建目录,如 Debug、Release等。
生成项目
项目目录结构确定之后,CMake 执行时会读取 CMakeLists.txt 并在构建目录中创建项目文件。开发人员通过选择某一种项目文件生成器来指定项目文件的类型。比如 Visual Studio 17 2022、Xcode、Unix Makefiles等。
有的生成器支持多配置(Debug,Release 等等),它允许开发人员在不同配置之间进行选择而不用重新执行 CMake,但也有一些不支持。
通常在执行 CMake 时要先切换到 CMakeLists.txt 所在目录,然后通过命令行工具执行如下命令:
cmake -G "Unix Makefiles" -B Build
如果 Build 目录不存在会自动创建,-G 选项省略时会选择宿主机默认构建平台生成器。CMake 3.15及以上版本可以通过 CMAKE_GENERATOR 环境变更来指定。在最后 CMake 会在控制台中打印出使用的配置,类似如下:
- Configuring done
-- Generating done
-- Build files have been written to: /some/path/buil
由此可见,该指令分为两个步骤,即配置(Configurate)和生成(Generate);
运行构建工具
此时,项目文件已准备就绪,开发人员便可以按照他们习惯的方式使用所选的构建工具。构建目录中包含必要的项目文件,这些文件可以导入到集成开发环境(IDE)中,并通过命令行工具进行读取。
此外,还可以通过 CMake 代为(调用构建工具)构建:
cmake --build /pathTo/build --config Debug --target MyApp
“–build”选项指定 CMake 项目生成步骤所使用的构建目录。对于多配置生成器,–config 选项用于指定要构建的配置;而单配置生成器则会忽略 --config 选项,转而依赖于在执行 CMake 项目生成步骤时所提供的信息。“–target”选项告诉构建工具要构建的内容,若未提供“–target”选项,则将按照默认目标进行构建。多个目标之间以空格隔开。
虽然开发人员通常会在日常开发过程中直接调用他们选定的构建工具,但像上面所示通过 cmake 命令来调用在驱动自动化构建的脚本中更具实用性。采用这种方法,一个简单的脚本化构建可能看起来像这样:
cmake -G "Unix Makefiles" -B build
cmake --build build --config Release --target MyApp
如果开发者想要尝试不同的生成器,那么只需更改传递给 cmake -G 选项的参数即可。其余部分无需改动。系统会自动调用正确的构建工具。即使构建工具不在用户的系统路径中,CMake --build 命令也能正常运行,但首次调用 CMake 进行配置时,可能需要将该工具添加到路径中。
最佳实践
1.独立的源目录和构建目录;
2.同一源目录对应多个构建目录(Debug,Release等);
3.不同的构建目录使用不同的生成器(如Unix Makefiles,XCode等);
4.定期使用不同于开发人员通常所使用的项目生成器来检查构建过程,能够大大减少未来可能出现的麻烦。避免编写不必要的针对特定生成器的代码;(这有助于发现对特定构建工具的任何意外依赖关系,或者能够检查不同生成类型之间的编译器设置是否存在差异。)
5.如果该项目已编写好脚本,则应使用 cmake --build 来调用构建工具,而非直接调用该构建工具。(这使得脚本能够轻松地在不同生成器类型之间切换,而无需修改构建命令。)
总之,一个良好的策略是确保该项目在每个感兴趣的平台上都采用默认的生成器类型,并再添加一种其他类型的生成器。

浙公网安备 33010602011771号