c++程序的打包编译cmake+make

发布于:2025-04-22 ⋅ 阅读:(56) ⋅ 点赞:(0)

c++打包编译


这篇博客是在上一篇博客的基础上增加了cmake的相关知识,更多打包和第3方库的情况,可以看下面这篇博客。

c++下程序的运行(第3方库的安装及安装gdal)_c++安装库-CSDN博客

1 在不用系统中打包介绍

1.1 linux中打包c++程序的2种方式

linux中工作中打包时,下面的第1种方式g++和第2种方式cmake+make都推荐,更倾向于第2种方式。

c++的2种打包方式

  • 方式一:使用g++编译器命令:
    第1种方式是使用g++命令,通过g++命令进行打包,但是可能需要一长串打包命令。但是对于简单的项目,打包命令就比较简单一些。

  • 方式二:使用cmake和make命令打包:
    编写CMakeLists.txt文件,通过cmake命令生成对应平台的makefile文件或.sln文件。最后使用make命令生成可执行程序或者第三方库。

  • 2种方式的对比:
    g++:
    适合小项目;

第2种方式:
自动处理路径分隔符、库依赖等平台差异。
支持生成多种构建系统(如 Makefile、Ninja、Xcode 项目等)。

1.2 windows中打包c++程序

c++常见的4种打包方式,另外还有好多种,不同的软件可以都会有自己的编译方式。

windows中打包文件,工作中只推荐2种方式:
第1种是使用集成开发环境自带的,比如vs就用vs的打包方式,clion就用clion打包方式。
第2种是用MinGW-win64软件的g++命令方式打包。

  • 方式一:Visual Studio 的MSVC编译的方式
    在这里插入图片描述

  • 方式二:使用cmake和其它构建工具命令打包:
    编写CMakeLists.txt文件,通过cmake命令生成对应平台的的makefile文件或.sln文件。最后使用MinGW、Ninja等命令生成可执行程序或者第三方库。
    在这里插入图片描述

  • 方式三:使用g++编译器命令:
    第1种方式是使用g++命令,通过g++命令进行打包,但是可能需要一长串打包命令。但是对于简单的项目,打包命令就比较简单一些。

在这里插入图片描述

  • 方式四:clion软件的编译方式
    在这里插入图片描述

1.3 cmake+Ninja和cmake+make的两种方式对比

1.3.1 Ninja是什么(可以认为是make工具的一个替代产品)

在这里插入图片描述

1.3.2 cmake+Ninja可以用于linux和windows系统中,编译效率比cmake+make更高

在这里插入图片描述在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

1.3.3 cmake+make可以用于linux系统中,不要在windows系统中用

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

1.4 cmake+make的编译方式只可以用于linux系统中,不能用于windows系统中,为什么还说可以跨平台使用呢?

cmake+make的编译方式只可以用于linux系统中,不能用于windows系统中。
说的跨平台这个概念方式,实际上专门指的是cmake这种方式,在windows中和linux中写1个CMakeLists.txt文件,然后就可以使用cmake工具在linux或windows中创建配置中间文件了,这里实现了跨平台。第2步编译的时候make只能用于linux中,是不能跨平台的。

1.5 安装g++、cmake、make软件

g++、cmake、make都是软件,如果要使用,必须先在电脑上进行安装好。然后添加到环境变量中

sudo yum install gcc gcc-c++
sudo yum install cmake
sudo yum install make

2 linux中第1种g++命令(直接但是复杂,不常用)


1 g++ -o executable_name source_file.cpp  // 编译普通文件
2 g++ -o your_program your_program.cpp -lgdal  // 编译带gdal包的文件,默认从环境变量找头文件和库文件。
3 g++ -o your_program your_program.cpp -I/path/to/gdal/include -L/path/to/gdal/lib -lgdal  // -I选项用于指定头文件路径,不涉及库文件,-L选项用于指定库文件所在的目录,-l选项用于指定库文件名。-lgdal指令会去找libgdal.a或者libgdal.so,-L和-l不管是动态库还是静态库都一样。-l选项后面跟的是库文件的名称,不需要包含文件扩展名。
4 g++ -o your_program your_program.cpp -I/path/to/gdal/include -Wl,-rpath,/path/to/gdal/lib -L/path/to/gdal/lib -lgdal  // 防止运行时找不到动态库文件,编译程序时使用-Wl,-rpath选项来指定运行时库文件的搜索路径。
 

在这里插入图片描述

1、编译时指定运行时的库文件,有时候在打包时,动态库本身依赖于其它动态库,这时候出现找不到的情况,可以使用-Wl,-rpath指定,可以指定多个路径,用冒号分隔:
g++ -o myapp src/main.cpp -L./lib -lmylib -Wl,-rpath=/path1:/path2

2、运行c++程序时,找不到动态库,可以使用export加进来,这样运行的时候就能找到第3方库了
export LD_LIBRARY_PATH=/path/to/libs:$LD_LIBRARY_PATH
./myapp

3 linux中第2种打包方式cmake命令+make命令(难但是方便,常用)

3.1 编译的流程

(1)准备好项目代码;
(2)编写CMakeLists.txt文件;
(3)创建指定文件夹并用cmake生成构建系统;
(4)make命令进行编译
(5)运行程序

3.1.1 第1步:准备好项目代码

在这里插入图片描述

3.1.2 第2步:编写CMakeLists.txt文件

在这里插入图片描述

3.1.3 第3步:创建指定文件夹并用cmake生成构建系统

创建单独的构建目录(推荐)进去再使用cmake,不要在根目录里使用cmake,这里约定俗成就是build目录,因为cmake会生成很多文件,如果之后重新编译等可以先把这个目录直接删除,而不用每个文件1个个删除。

# 进入项目目录
cd my_project

# 创建构建目录(推荐使用out-of-source构建)
mkdir build
cd build

# 生成构建系统(根据你的系统选择生成器)
# 在Linux/macOS上:
cmake ..

# 在Windows上(如果使用Visual Studio):
# cmake .. -G "Visual Studio 16 2019"

3.1.4 第4步:编译项目

# 编译项目
# 或者在Linux/macOS上也可以直接使用make(如果cmake生成的是Makefile)
make

# 也可以用这个命令
cmake --build .

3.1.5 第5步:运行程序

在这里插入图片描述

3.2 几个疑问点解释

3.2.1 为什么要创建build文件夹

在这里插入图片描述

3.2.2 cmake命令为什么是cmake …

在这里插入图片描述

3.2.3 cmake …为什么能够找到上级目录的CMakeLists.txt文件?并没有指定CMakeLists.txt文件呀?

CMake 默认会在指定目录中查找名为 CMakeLists.txt 的文件,这是 CMake 的内置约定,所有 CMake 项目都遵循这一规则。
在这里插入图片描述
在这里插入图片描述

3.2.4 cmake具体干了什么?

在这里插入图片描述

3.3 cmake和make的区别

  • cmake … 只做配置,是一个生成配置的软件。
    它解析 CMakeLists.txt,检查环境,生成构建系统文件(如 Makefile),但不会调用编译器。
  • make 或 cmake --build . 才是编译
    它们根据生成的构建系统文件,实际调用 g++/clang/msvc 等编译器生成二进制文件。
  • cmake … 不会直接生成可执行文件,它只是准备构建环境。必须再执行 make 或 cmake --build . 才会真正编译代码。使用2步而不是1步主要是因为CMake 的分离配置和编译的设计哲学。
  • cmake这种设计提高了跨平台灵活性,也是现代构建系统的通用模式。它会根据

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

3.4 第2种cmake+make打包方法为什么能够实现跨平台?实现跨平台是cmake的功劳还是make的功劳?

  • CMake 是跨平台灵活性的核心实现者,它通过抽象平台差异,生成适合当前环境的构建系统。

  • Make 是平台相关的执行工具,其本身不具备跨平台能力,依赖 CMake 为它生成平台适配的 Makefile。

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

3.5 只有在linux中编译c++代码才能使用第2种cmake+make打包方法,在windows中 使用CMake + 构建工具(如 Make/Ninja/MSBuild) 的组合

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

4 cmake的1个案例和相关语法

# 设置CMake最低版本要求
cmake_minimum_required(VERSION 3.10)

# 定义项目名称和使用的语言(CXX表示C++)
project(MyProject LANGUAGES CXX)

# 设置C++标准为C++17
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

# 查找OpenCV库(需要提前安装)
find_package(OpenCV REQUIRED)

# 设置头文件搜索路径,使用空格或者换行分割多个路径
include_directories(
    ${OpenCV_INCLUDE_DIRS}  # OpenCV头文件路径
    include                 # 项目主include目录
    include/utils          # 项目子目录中的头文件
    include/core           # 项目子目录中的头文件
    third_party/include    # 第三方库头文件
)

# 设置动态库搜索路径,使用空格或者换行分割多个路径
link_directories(
    lib                    # 项目主库目录
    lib/x64               # 项目子目录中的库
    third_party/lib       # 第三方库目录
    ${OpenCV_LIBRARY_DIRS} # OpenCV库路径
)

# 收集所有源文件,递归查找
file(GLOB_RECURSE SOURCES "src/*.cpp" "src/*.cc")

# 添加可执行文件
add_executable(${PROJECT_NAME} ${SOURCES})

# 链接库文件,使用空格或者换行分割多个库
target_link_libraries(${PROJECT_NAME}
    ${OpenCV_LIBS}        # OpenCV库
    utils                 # 项目内部库
    core                  # 项目内部库
    pthread               # 系统线程库
    dl                    # 动态加载库
)

1、使用cmake进行打包,包含可执行程序和动态依赖库_cmake 打包-CSDN博客

2、CMake 基本常用语法 CMakeLists.txt_cmakelist语法下载-CSDN博客

3 CMake常用命令_cmake命令-CSDN博客

5 make的相关语法进一步介绍

在这里插入图片描述