百度360必应搜狗淘宝本站头条
当前位置:网站首页 > IT知识 > 正文

必读干货|使用Cmake管理C++项目简明教程

liuian 2025-01-21 19:28 50 浏览

一、背景

Cmake是 kitware公司以及一些开源开发者在开发几个工具套件(VTK)的过程中衍生品,最终形成体系,成为一个独立的开源项目。其官方网站是 cmake.org,可以通过访问官方网站获得更多关于cmake的信息。

它是一个跨平台的编译(Build)工具,可以用简单的语句来描述所有平台的编译过程。CMake能够输出makefile文件,然后系统会根据这个makefile文件内容编译整个工程。

图1 kitware公司和Cmake套件

软件开发有以下三个步骤:

1.编译源代码;

2.链接到其他库;

3.将应用程序打包为库或二进制文件。

假如我们有一个大型的C++项目,由非常多的互相调用的工程共同组成,一些用于生成库文件,一些用于实现逻辑功能。他们之间的调用关系复杂而严格,如果想在这样复杂的框架下进行二次开发,显然只拥有它的源码是远远不够的,还需要清楚的明白这几十个项目之间的复杂关系。即使是原作者给出了相关的结构文档,对新手来说建立工程的过程依旧是漫长而艰辛的,开发人员的核心业务是软件开发,而不是软件构建。Cmake目的是实现软件构建流程的自动化,并且是跨平台的。

原作者只需要生成一份CMakeLists.txt文档,框架的使用者们只需要在下载源码的同时下载作者提供的CMakeLists.txt,就可以利用CMake,在原作者的帮助下进行工程的搭建。Cmake编写的过程实际上是编程的过程,不过你需要编写的是 CMakeLists.txt(一般情况下每个目录一个),使用的是“Cmake”语言和语法。

刚入门的开发者拿到Cmakelist看着一脸雾水,里面众多的语法指令不知道是什么含义甚至不能自己修改,本文接下来将介绍Cmakelist的各种重要的变量、指令、语句及其作用。

图2 Cmake的构建流程

二、安装

大多数Linux的操作系统会在系统中直接包含,不必手动安装。其他操作系统,比如:Windows或者某些Linux系统,可以从Cmake官网上下载安装包进行安装:cmake.org/HTML/Download。安装步骤省略,可以借鉴网上其他资料。

三、使用

因为cmake会生成一些中间文件(CMakeFiles,CMakeCache.txt, cmake_install.cmake, Makefile),所以最好在项目源代码目录重新建一个文件夹存放生成的中间文件,即外部编译。在中间文件夹中依次执行编译指令cmake ..,make,那么编译器会按照生成的Makefile中的指令编译C++工程。如果要对编译的结果清理,使用make clean 指令即可。在 Windows 上,还可以使用 CMakeSetup (GUI)进行工程构建。

make install命令将编译好的目标文件默认直接安装到/usr/local目录,如果想安装到其他目录,可以使用make install DESTDIR=< install_path >。

本文接下来介绍Cmakelist的编写方法,这是开发者最关心的地方。Cmakelist编写指令时不区分大小写,为了统一风格,本文使用大写字母。

四、基础指令

要编译非常简单的C++工程,工程不依赖第三方库,那么Cmakelist中至少包含以下内容:

#声明要求的最低Cmake版本

CMAKE_MINIMUM_REQUIRED(VERSIN 2.8)

#Cmake工程名。这个指令隐式的定义了两个 cmake变量: PROJECT_BINARY_DIR以及PROJECT_SOURCE_DIR。分别指向项目的编译路径和工程路径。

PROJECT (HELLO)

#生成可执行文件,${}来引用变量。

ADD_EXECUTABLE(Executable program name ${ Source files })

到这里,一个可执行程序就生成了。如果要管理依赖第三方库的工程,就需要加入一些额外指令。除此之外,还有一些Cmake中重要的变量和语句需要掌握,才能使用起来得心应手。在下面列出:

五、重要的变量

#Cmake版本

CMAKE_SYSTEM_VERSION

#可执行文件的输出路径

EXECUTABLE_OUTPUT_PATH

#库文件输出路径

LIBRARY_OUTPUT_PATH

#安装路径

CMAKE_INSTALL_PREFIX

Note:该变量可以在Cmakelist中显式地定义,即:SET(CMAKE_INSTALL_PREFIX < install_path >);也可以作为命令行参数传递:cmake -DCMAKE_INSTALL_PREFIX=< install_path > ;还可以在cmake完成后使用make install DESTDIR=< install_path >指定安装路径。

#工程编译时存放二进制文件的目录。

CMAKE_BINARY_DIR

#将添加的头文件搜索路径放在已有路径的前面。

CMAKE_INCLUDE_DIRECTORIES_BEFORE

#将添加的头文件搜索路径放在已有路径的后面。

CMAKE_INCLUDE_DIRECTORIES_ AFTER

#工程顶层目录

CMAKE_SOURCE_DIR

#定义自己的 cmake模块所在的路径

CMAKE_MODULE_PATH

#控制库的默认编译方式

BUILD_SHARED_LIBS

#设置 C++/C的编译选项,也可以通过指令 ADD_DEFINITIONS()添加

CMAKE_CXX_FLAGS/ CMAKE_CXX_FLAGS

Note:该指令非常重要,因为它能选择C++/C工程的编译器行为。有时候我们依赖的第三方库的编译方式与自己项目的编译方式不一致时,编译会通过,但是运行时出现非常隐蔽的bug。此时就需要检查,项目中各种库的编译行为是否一致。

# 设置构建类型,类型选项有Debug/Release。当使用GDB调试工程时要使用Debug选项。该变量可以通过命令行:cmake -DCMAKE_BUILD_TYPE=Release或指令SET(CMAKE_BUILD_TYPE [type])设置。

CMAKE_BUILD_TYPE

六、重要的指令和语句

#查看Cmake生成的详细编译信息,相当于执行make VERBOSE=1。当构建失败并且需要找出原因时使用该条指令非常有帮助。

SET(CMAKE_VERBOSE_MAKEFILE on )

#显式的为变量赋值,非常重要

SET(VAR [VALUE] [CACHE TYPE DOCSTRING [FORCE]])

#用来寻找第三方库的Find<name>.cmake模块,该模块里提供了库的头文件路径和库文件路径。如果找不到,通过设置 CMAKE_MODULE_PATH 变量来告诉 Cmake 在哪里找到它。

FIND_PACKAGE(<name> [major.minor] [QUIET] [NO_MODULE] [[REQUIRED|COMPONENTS] [componets...]])

Note:编译一个链接第三方库的软件时,我们需要知道该库的头文件路径、库文件路径、要链接的库的文件名。使用第三方库时必须在Cmakelist中提供这些信息。

#向终端输出用户定义的信息,显示状态信息、警告或错误。包含了三种类型:SEND_ERRO、SATUS、FATAL_ERROR。

MESSAGE([SEND_ERROR | STATUS | FATAL_ERROR] "message to display"...)

例:MESSAGE(STATUS "This is SOURCE dir "${HELLO_SOURCE_DIR})

#添加可执行文件

ADD_EXECUTABLE(<name> IMPORTED [GLOBAL])

#向当前工程添加存放源文件的子目录,并指定中间二进制和目标二进制存放的位置。

ADD_SUBDIRECTORY(source_dir [binary_dir] )

#生成库。生成的库的类型有三种:SHARED,动态库;STATIC,静态库;MODULE,在使用 dyld的系统有效。

ADD_LIBRARY(libname [SHARED|STATIC|MODULE] [EXCLUDE_FROM_ALL] source1 source2 ... sourceN)

#设置输出目标的属性

SET_TARGET_PROPERTIES(target1 target2 ...PROPERTIES prop1 value1 prop2 value2 ...)

例:设置目标库的名称:SET_TARGET_PROPERTIES(taget_name PROPERTIES OUTPUT_NAME "hello")

#设置动态库的版本号,VERSION指代动态库版本,SOVERSION指代 API版本。

SET_TARGET_PROPERTIES(hello PROPERTIES VERSION 1.2 SOVERSION 1)

#向工程添加多个特定的头文件搜索路径。系统默认的头文件路径是/usr/include和/usr/local/include,如果不是,需要在Cmakelist中显式的定义。

INCLUDE_DIRECTORIES([AFTER|BEFORE] [SYSTEM] dir1 dir2 ...)

#将目标文件链接到第三方库,非常重要的语句

TARGET_LINK_LIBRARIES(target library1<debug | optimized> library2...)

#在指定路径中搜索文件名,指定路径指的是环境变量CMAKE_INCLUDE_PATH中包含的所有路径。

FIND_PATH(filename)

#向 C/C++编译器添加-D定义。修改预处理器设置

ADD_DEFINITIONS()

#定义 target依赖的其他 target,确保在编译本 target之前,其他的 target已经被构建

ADD_DEPENDENCIES()

#搜索一个目录下所有的源代码文件并将列表存储在一个变量,可以与ADD_EXECUTABLE连用。

AUX_SOURCE_DIRECTORY(. SRC_LIST)

ADD_EXECUTABLE(main ${SRC_LIST})

#if语句, 如果表达式内容不是:空,0,N, NO, OFF, FALSE, NOTFOUND或<var>_NOTFOUND时,表达式为真。

IF(expression)

…..

ELSE(expression)

…..

ENDIF(expression)

#列表变量遍历语句

FOREACH(loop_var)

...

ENDFOREACH(loop_var)

#while语句

WHILE(condition)

...

ENDWHILE(condition)

本文提到的变量、语句、指令包含了Cmakelist编写时最常见、最重要的部分,编写Cmake的过程其实就是编程的过程。

相关推荐

驱动网卡(怎么从新驱动网卡)
驱动网卡(怎么从新驱动网卡)

网卡一般是指为电脑主机提供有线无线网络功能的适配器。而网卡驱动指的就是电脑连接识别这些网卡型号的桥梁。网卡只有打上了网卡驱动才能正常使用。并不是说所有的网卡一插到电脑上面就能进行数据传输了,他都需要里面芯片组的驱动文件才能支持他进行数据传输...

2026-01-30 00:37 liuian

win10更新助手装系统(微软win10更新助手)

1、点击首页“系统升级”的按钮,给出弹框,告诉用户需要上传IMEI码才能使用升级服务。同时给出同意和取消按钮。华为手机助手2、点击同意,则进入到“系统升级”功能华为手机助手华为手机助手3、在检测界面,...

windows11专业版密钥最新(windows11专业版激活码永久)

 Windows11专业版的正版密钥,我们是对windows的激活所必备的工具。该密钥我们可以通过微软商城或者通过计算机的硬件供应商去购买获得。获得了windows11专业版的正版密钥后,我...

手机删过的软件恢复(手机删除过的软件怎么恢复)
手机删过的软件恢复(手机删除过的软件怎么恢复)

操作步骤:1、首先,我们需要先打开手机。然后在许多图标中找到带有[文件管理]文本的图标,然后单击“文件管理”进入页面。2、进入页面后,我们将在顶部看到一行文本:手机,最新信息,文档,视频,图片,音乐,收藏,最后是我们正在寻找的[更多],单击...

2026-01-29 23:55 liuian

一键ghost手动备份系统步骤(一键ghost 备份)

  步骤1、首先把装有一键GHOST装系统的U盘插在电脑上,然后打开电脑马上按F2或DEL键入BIOS界面,然后就选择BOOT打USDHDD模式选择好,然后按F10键保存,电脑就会马上重启。  步骤...

怎么创建局域网(怎么创建局域网打游戏)

  1、购买路由器一台。进入路由器把dhcp功能打开  2、购买一台交换机。从路由器lan端口拉出一条网线查到交换机的任意一个端口上。  3、两台以上电脑。从交换机任意端口拉出网线插到电脑上(电脑设置...

精灵驱动器官方下载(精灵驱动手机版下载)

是的。驱动精灵是一款集驱动管理和硬件检测于一体的、专业级的驱动管理和维护工具。驱动精灵为用户提供驱动备份、恢复、安装、删除、在线更新等实用功能。1、全新驱动精灵2012引擎,大幅提升硬件和驱动辨识能力...

一键还原系统步骤(一键还原系统有哪些)

1、首先需要下载安装一下Windows一键还原程序,在安装程序窗口中,点击“下一步”,弹出“用户许可协议”窗口,选择“我同意该许可协议的条款”,并点击“下一步”。  2、在弹出的“准备安装”窗口中,可...

电脑加速器哪个好(电脑加速器哪款好)

我认为pp加速器最好用,飞速土豆太懒,急速酷六根本不工作。pp加速器什么网页都加速,太任劳任怨了!以上是个人观点,具体性能请自己试。ps:我家电脑性能很好。迅游加速盒子是可以加速电脑的。因为有过之...

任何u盘都可以做启动盘吗(u盘必须做成启动盘才能装系统吗)

是的,需要注意,U盘的大小要在4G以上,最好是8G以上,因为启动盘里面需要装系统,内存小的话,不能用来安装系统。内存卡或者U盘或者移动硬盘都可以用来做启动盘安装系统。普通的U盘就可以,不过最好U盘...

u盘怎么恢复文件(u盘文件恢复的方法)

开360安全卫士,点击上面的“功能大全”。点击文件恢复然后点击“数据”下的“文件恢复”功能。选择驱动接着选择需要恢复的驱动,选择接入的U盘。点击开始扫描选好就点击中间的“开始扫描”,开始扫描U盘数据。...

系统虚拟内存太低怎么办(系统虚拟内存占用过高什么原因)

1.检查系统虚拟内存使用情况,如果发现有大量的空闲内存,可以尝试释放一些不必要的进程,以释放内存空间。2.如果系统虚拟内存使用率较高,可以尝试增加系统虚拟内存的大小,以便更多的应用程序可以使用更多...

剪贴板权限设置方法(剪贴板访问权限)
剪贴板权限设置方法(剪贴板访问权限)

1、首先打开iphone手机,触碰并按住单词或图像直到显示选择选项。2、其次,然后选取“拷贝”或“剪贴板”。3、勾选需要的“权限”,最后选择开启,即可完成苹果剪贴板权限设置。仅参考1.打开苹果手机设置按钮,点击【通用】。2.点击【键盘】,再...

2026-01-29 21:37 liuian

平板系统重装大师(平板重装win系统)

如果你的平板开不了机,但可以连接上电脑,那就能好办,楼主下载安装个平板刷机王到你的个人电脑上,然后连接你的平板,平板刷机王会自动识别你的平板,平板刷机王上有你平板的我刷机包,楼主点击下载一个,下载完成...

联想官网售后服务网点(联想官网售后服务热线)

联想3c服务中心是联想旗下的官方售后,是基于互联网O2O模式开发的全新服务平台。可以为终端用户提供多品牌手机、电脑以及其他3C类产品的维修、保养和保险服务。根据客户需求层次,联想服务针对个人及家庭客户...