++项目 cmake头文件路径_基于VSCode和CMake进行C/C++开发第六讲CMake

2023-05-16

6.0:本讲目录

本系列视频,B站首发,up主: xiaobing1016

c8a86d9219a92a5d25f7bf918a3fe9ce.png

前言

  • CMake是一个跨平台的安装编译工具,可以用简单的语句来描述所有平台的安装(编译过程)。

  • CMake可以说已经成为大部分C++开源项目标配

6.1 Cross-platform development

Let’s assume you have some cross-platform project with C++ code shared along different platforms/IDEs. Say you use Visual Studio on Windows, Xcode on OSX and Makefile for Linux:

9c80d1b499bbbee21ca1db157188f9dc.png

What you will do if you want to add new bar.cpp source file? You have to add it to every tool you use:

74fcc40480f8376d8323105868d1aa7c.png

To keep the environment consistent you have to do the similar update several times. And the most important thing is that you have to do it manually (arrow marked with a red color on the diagram in this case). Of course such approach is error prone and not flexible.

CMake solve this design flaw by adding extra step to development process. You can describe your project in CMakeLists.txt file and use CMake to generate tools you currently interested in using cross-platform CMake code:

ed45cac8c6124a78fa836ce3651f4b74.png

Same action - adding new bar.cpp file, will be done in one step now:

b48561d35fa9ece1db3ef54a78b76b91.png

Note that the bottom part of the diagram was not changed. I.e. you still can keep using your favorite tools like Visual Studio/msbuild, Xcode/xcodebuild and Makefile/make!

6.2 语法特性介绍

  • 基本语法格式:指令(参数 1 参数 2…)

    • 参数使用括弧括起

    • 参数之间使用空格分号分开

  • 指令是大小写无关的,参数和变量是大小写相关的

    1set(HELLO hello.cpp)
    2add_executable(hello main.cpp hello.cpp)
    3ADD_EXECUTABLE(hello main.cpp ${HELLO})
  • 变量使用${}方式取值,但是在 IF 控制语句中是直接使用变量名

6.3 重要指令和CMake常用变量

6.3.1 重要指令

  • cmake_minimum_required - 指定CMake的最小版本要求

    1# CMake最小版本要求为2.8.3
    2cmake_minimum_required(VERSION 2.8.3)
    • 语法:cmake_minimum_required(VERSION versionNumber [FATAL_ERROR])

  • project - 定义工程名称,并可指定工程支持的语言  

    1# 指定工程名为HELLOWORLD
    2project(HELLOWORLD)
    • 语法:project(projectname [CXX] [C] [Java])

  • set - 显式的定义变量  

    1# 定义SRC变量,其值为main.cpp hello.cpp
    2set(SRC sayhello.cpp hello.cpp)
    • 语法:set(VAR [VALUE] [CACHE TYPE DOCSTRING [FORCE]])

  • include_directories - 向工程添加多个特定的头文件搜索路径  --->相当于指定g++编译器的-I参数

    1# 将/usr/include/myincludefolder 和 ./include 添加到头文件搜索路径
    2include_directories(/usr/include/myincludefolder ./include)
    • 语法:include_directories([AFTER|BEFORE] [SYSTEM] dir1 dir2 …)

  • link_directories - 向工程添加多个特定的库文件搜索路径  --->相当于指定g++编译器的-L参数

    1# 将/usr/lib/mylibfolder 和 ./lib 添加到库文件搜索路径
    2link_directories(/usr/lib/mylibfolder ./lib)
    • 语法:link_directories(dir1 dir2 …)  

  • add_library - 生成库文件

    1# 通过变量 SRC 生成 libhello.so 共享库
    2add_library(hello SHARED ${SRC})
    • 语法:add_library(libname [SHARED|STATIC|MODULE] [EXCLUDE_FROM_ALL] source1 source2 … sourceN)

  • add_compile_options - 添加编译参数

    1# 添加编译参数 -Wall -std=c++11
    2add_compile_options(-Wall -std=c++11 -O2)
    • 语法:add_compile_options(

  • add_executable - 生成可执行文件

    1# 编译main.cpp生成可执行文件main
    2add_executable(main main.cpp)
    • 语法:add_library(exename source1 source2 … sourceN)

  • target_link_libraries - 为 target 添加需要链接的共享库  --->相同于指定g++编译器-l参数

    1# 将hello动态库文件链接到可执行文件main
    2target_link_libraries(main hello)
    • 语法:target_link_libraries(target library1library2…)

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

    1# 添加src子目录,src中需有一个CMakeLists.txt
    2add_subdirectory(src)
    • 语法:add_subdirectory(source_dir [binary_dir] [EXCLUDE_FROM_ALL])

  • aux_source_directory - 发现一个目录下所有的源代码文件并将列表存储在一个变量中,这个指令临时被用来自动构建源文件列表

    1# 定义SRC变量,其值为当前目录下所有的源代码文件
    2aux_source_directory(. SRC)
    3# 编译SRC变量所代表的源代码文件,生成main可执行文件
    4add_executable(main ${SRC})
    • 语法:aux_source_directory(dir VARIABLE)

6.3.2 CMake常用变量

  • CMAKE_C_FLAGS   gcc编译选项

    CMAKE_CXX_FLAGS  g++编译选项

    1# 在CMAKE_CXX_FLAGS编译选项后追加-std=c++11
    2set( CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")

    CMAKE_BUILD_TYPE  编译类型(Debug, Release)

    1# 设定编译类型为debug,调试时需要选择debug
    2set(CMAKE_BUILD_TYPE Debug) 
    3# 设定编译类型为release,发布时需要选择release
    4set(CMAKE_BUILD_TYPE Release) 

    CMAKE_BINARY_DIR

    PROJECT_BINARY_DIR

    __BINARY_DIR

  1. 这三个变量指代的内容是一致的。

  2. 如果是 in source build,指的就是工程顶层目录。

  3. 如果是 out-of-source 编译,指的是工程编译发生的目录。

  4. PROJECT_BINARY_DIR 跟其他指令稍有区别,不过现在,你可以理解为他们是一致的。

CMAKE_SOURCE_DIR

PROJECT_SOURCE_DIR__SOURCE_DIR

  1. 这三个变量指代的内容是一致的,不论采用何种编译方式,都是工程顶层目录。

  2. 也就是在 in source build时,他跟 CMAKE_BINARY_DIR 等变量一致。

  3. PROJECT_SOURCE_DIR 跟其他指令稍有区别,现在,你可以理解为他们是一致的。


  • CMAKE_C_COMPILER:指定C编译器

  • CMAKE_CXX_COMPILER:指定C++编译器

  • EXECUTABLE_OUTPUT_PATH:可执行文件输出的存放路径

  • LIBRARY_OUTPUT_PATH:库文件输出的存放路径

6.4 CMake编译工程

CMake目录结构:项目主目录存在一个CMakeLists.txt文件

两种方式设置编译规则

  1. 包含源文件的子文件夹包含CMakeLists.txt文件,主目录的CMakeLists.txt通过add_subdirectory添加子目录即可;

  2. 包含源文件的子文件夹未包含CMakeLists.txt文件,子目录编译规则体现在主目录的CMakeLists.txt中;

6.4.1 编译流程

在 linux 平台下使用 CMake 构建C/C++工程的流程如下:

  • 手动编写 CmakeLists.txt。

  • 执行命令 cmake PATH生成 Makefile ( PATH 是顶层CMakeLists.txt 所在的目录 )。

  • 执行命令make 进行编译。


1# important tips
2.          # 表示当前目录
3./         # 表示当前目录
4
5..      # 表示上级目录
6../     # 表示上级目录

6.4.2 两种构建方式

  • 内部构建(in-source build):不推荐使用

    内部构建会在同级目录下产生一大堆中间文件,这些中间文件并不是我们最终所需要的,和工程源文件放在一起会显得杂乱无章。

    1## 内部构建
    2
    3# 在当前目录下,编译本目录的CMakeLists.txt,生成Makefile和其他文件
    4cmake .
    5# 执行make命令,生成target
    6make
  • 外部构建(out-of-source build):==推荐使用==

    将编译输出文件与源文件放到不同目录中

     1## 外部构建
    2
    3# 1. 在当前目录下,创建build文件夹
    4mkdir build 
    5# 2. 进入到build文件夹
    6cd build
    7# 3. 编译上级目录的CMakeLists.txt,生成Makefile和其他文件
    8cmake ..
    9# 4. 执行make命令,生成target
    10make

6.5 【实战】CMake代码实践

针对第五章写的两个小项目来写对应的CMakeLists.txt

6.5.1 最小CMake工程

1# Set the minimum version of CMake that can be used
2cmake_minimum_required(VERSION 3.0)
3
4# Set the project name
5project (HELLO)
6
7# Add an executable
8add_executable(hello_cmake main.cpp)

6.5.2 多目录工程 - 直接编译

 1# Set the minimum version of CMake that can be used
2cmake_minimum_required(VERSION 3.0)
3
4#project name
5project(SWAP)
6
7#head file pat
8include_directories( include )
9
10#source directory files to var
11add_subdirectory( src DIR_SRCS )
12
13#add executable file  
14add_executable(swap_02 ${TEST_MATH})
15
16#add link library  
17target_link_libraries(${FS_BUILD_BINARY_PREFIX}sqrt ${LIBRARIES}) 

6.5.3 多目录工程 - 生成库编译

 1# Set the minimum version of CMake that can be used
2cmake_minimum_required(VERSION 3.0)
3
4#project name  
5project(SWAP_LIBRARY)
6
7#add compile options
8add_compile_options("-Wall -std=c++11")
9
10#set CMAKE_BUILD_TYPE
11set( CMAKE_BUILD_TYPE Debug ) 
12
13# set output binary path  
14set(EXECUTABLE_OUTPUT_PATH ${PROJECT_BINARY_DIR}/bin)
15
16############################################################
17# Create a library
18############################################################
19
20#Generate the static library from the library sources
21add_library( swap_library STATIC src/Swap.cpp )
22
23target_include_directories( swap_lib PUBLIC ${PROJECT_SOURCE_DIR}/include )
24
25############################################################
26# Create an executable
27############################################################
28
29# Add an executable with the above sources
30add_executable( swap_01 main.cpp )
31
32# link the new swap_01 target with the swap_lib target
33target_link_libraries( swap_01 swap_liby )

END

4395b051-4552-eb11-8da9-e4434bdf6706.svg 2e5f0b00569c62b9da41a021914bcdf6.png

扫码关注公众号

微信号 : iVSCode

bilibili  : xiaobing1016

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

++项目 cmake头文件路径_基于VSCode和CMake进行C/C++开发第六讲CMake 的相关文章

  • [转]C++ 使用 curl 进行 http 请求(GET、POST、Download)的封装

    原文连接 xff1a https www cnblogs com oftenlin p 9478067 html CommonTools h CommonTools h Created on 2018年8月2日 Author didi in
  • [转]使用 curl 发送 POST 请求的几种方式

    HTTP 的 POST 请求通常是用于提交数据 xff0c 可以通过这篇文章来了解各种提交方式 xff1a 四种常见的 POST 提交数据方式 做 Web 后端开发时 xff0c 不可避免地要自己给自己发请求来调试接口 xff0c 这里要记
  • 人生进度条百分之20_人生进度条——27%

    嗨 xff5e 我们又见面啦 嘿 小吕这次有好多好多想要和你分享的东西 xff5e Part 01 人生进度条 假如我这一辈子有幸能活到75岁 xff0c 那我的人生就只有九百个月 从没仔细想过 xff0c 今年我20岁 xff0c 原来已
  • Linux用curl调用应用接口

    很多同学都用postman测试过后台应用接口 xff0c 的确非常方便 今天这里介绍一下在Liunx下用curl命令测试接口的方法和遇到的一些问题 xff0c 包括url传参转义和中文传参报错的问题 xff0c 这里都提供解决办法 下面我们
  • http.request请求及在node中post请求参数解析

    Post请求 var http 61 require 39 http 39 var qs 61 require 39 querystring 39 var post data 61 a 123 time new Date getTime 这
  • 网络调试助手的使用 调试TCP,UDP

    网络调试助手是集TCP UDP服务端客户端一体的网络调试工具 xff0c 可以帮助网络应用设计 开发 测试人员检查所开发的网络应用软硬件的数据收发状况 xff0c 提高开发的速度 xff0c 是TCP UDP应用开发助手 集成TCP UDP
  • EasyDarwin开源流媒体云平台之云台ptz控制设计与实现

    本文转自EasyDarwin开源团队成员Alex的博客 xff1a http blog csdn net cai6811376 article details 51912692 近日 xff0c EasyDarwin云平台加入云台控制功能
  • 字节与比特序

    软件和硬件工程师不得不处理字节及比特序问题 xff0c 这个过程就像走迷宫 尽管最终我们能够走出来 xff0c 但我们往往筋疲力尽 本文尝试对字节和比特序发挥影响力的领域 xff0c 包括CPU xff0c 总线 xff0c 设备及网络协议
  • 手把手教你新建MSP432工程

    MSP432是德州仪器推出的新一款高性能低功耗处理器 xff0c Cortex M4内核 xff0c 较430相比处理能力大大增强 xff0c 同时采用了430设计的低功耗技术 xff0c 和传统ARM相比功耗更低 xff0c 相信在不久的
  • boost异步tcp通信技术练习

    本例演示了基本的boost异步tcp服务器程序的编写 演示程序的构思是这样的 xff1a 服务端 xff1a l 控制台程序 xff1b l 侦听客户端连接 xff0c 当有新连接时 xff0c 在屏幕上打印消息 xff1b l 当收到客户
  • CSPS模拟 59

    经ooo提醒咕题解会掉rp 我反正也 冒着改不完题的风险 xff0c 就开始颓博了 话说好久没这么舒坦的垫过底了233 上来一看T1 xff0c 立刻就转化题意为有奇偶性和距离限制的bfs 然后就没考虑子串不能越过母串边界的事 xff0c
  • vmware使用open-vm-tools配置ubuntu共享文件夹

    vmware下安装ubuntu 18 04后 xff0c 按往常的惯例安装vmware tools xff0c 安装时提示建议使用open vm tools xff0c 于是放弃vmware tools的安装 xff0c 尝试使用open
  • CSPS模拟 58

    爆炸 没算内存见祖宗 为什么偏偏这次卡内存我没算 T1 HashMap各种水 T2 智障背包 xff01 但是卡内存 xff01 T3 Dashspeed 考试用点分治 43 线段树水到了80 实际上是个没见过的套路题 在之前的思维定势里
  • CentOS 修改/etc/resolv.conf 重启network后又恢复到原来的状态?

    问题描述 xff1a CentOS 修改 etc resolv conf 执行service network restart后 xff0c etc resolv conf又恢复到原来的状态 解决方法 xff1a etc resolv con
  • video实现有声音自动播放

    video实现自动播放有声音 需求 xff1a 老板见人家可以的 xff0c 我们的也要可以 xff01 xff01 xff01 前端 xff1a 自动播放 xff0c 简单 要实现 xff1a 鼠标移入视频播放同时有声音 xff0c 移出
  • ArcGIS栅格影像怎么从WGS84地理坐标转成Xian80投影坐标

    事情是这样的 xff0c 我下载了一个WGS84坐标系的影像图 xff0c 需要加载到Xian80投影坐标系下 xff0c 所以需要对影像图进行坐标系的转换 1 因为涉及到两个参考椭球的问题 xff0c 首先需要计算七参数 xff0c 如何
  • [Mac]如何让两个窗口各占半个屏幕

    微信公众号 xff1a 山青咏芝 xff08 shanqingyongzhi xff09 博客园地址 xff1a 山青咏芝 xff08 https www cnblogs com strengthen xff09 GitHub地址 xff1
  • XP访问WIN10共享打印机提示错误:操作无法完成,拒绝访问

    XP系统添加打印机 连接到此计算机的本地打印机 xff08 取消自动检测 xff09 创建新端口 xff08 LOCAL port xff09 输入端口名 计算机名 打印机名 xff08 例如 xff1a adubei HP lasjet
  • linux 环境下如何完全卸载postgres

    完全删除postgres 小笔记 xff1a 1 查看版本号和系统类别 xff1a cat etc redhat realease 2 如果是redhat yum install a yum 删除软件包 xff1a yum remove p
  • odroid xu4

    1 sd 2 flashing image 3 GParted 4 ROS install 5 make an image span class pln sudo dd span class kwd if span class pun 61

随机推荐