上面几个教程我们的程序都是生成可执行文件。但是我们在合作开发算法的时候经常需要交付的是一个模块,该模块提供特定的算法功能,用于给整体的项目进行调用。但我们又不能直接提供源码,所以我们可以提供一个库文件(静态库或者动态库),配置接口文件可以在不提供源代码的情况下给他人提供算法模块功能。本文主要讲述如何使用CMakeLists.txt,配置生成动态和静态库文件。
本教程的使用环境为:
代码语言:javascript
复制
ubutu18.04 lts
gcc version 7.5.0
g++ version 7.5.0
cmake version 3.10.2
安装cmake:
代码语言:javascript
复制
sudo apt install cmake
配置输出库文件(lib和so)主要是通过函数add_subdirectory进行配置,使用STATIC表示静态库(lib),SHARED表示动态库(so)。同时可以使用SET_TARGET_PROPERTIES函数可以设置库文件的版本。
首先,看一下整体的目录结构:
代码语言:javascript
复制
|-- tutorial_fourth/
|-- src/
|-- tutorial.cpp
|-- include/
|--TutorialConfig.h.in
|-- mathlib/
|-- CMakeLists.txt
|-- mathlib.h
|-- mathlib.cpp
|-- CMakeLists.txt
根目录下的CMakeLists.txt文件为:
代码语言:javascript
复制
# 设置cmake的最低版本
cmake_minimum_required(VERSION 3.10)
# 设置工程名称 和版本
project(tutorial VERSION 1.0)
# 设置指定的C++编译器版本是必须的,如果不设置,或者为OFF,则指定版本不可用时,会使用上一版本。
set(CMAKE_CXX_STANDARD_REQUIRED ON)
# 指定为C++11 版本
set(CMAKE_CXX_STANDARD 11)
# 提供一个选项是OFF或者ON,如果没有初始值被提供则默认使用OFF
option(USE_MYMATH "Use tutorial provided math implementation" ON)
# 指定版本号的配置文件
configure_file(include/TutorialConfig.h.in TutorialConfig.h)
# 判断变量USE_MYMATH是否设置了ON,如果设置了配置mathlib library
if(USE_MYMATH)
# 添加一个名字为mathlib的子编译路径
add_subdirectory(mathlib)
# 列出mathlib库的所有项目,并添加到外部库变量EXTRA_LIBS中
list(APPEND EXTRA_LIBS mathlib)
# 将子路径"${PROJECT_SOURCE_DIR}/mathlib"添加到外部路径变量EXTRA_INCLUDES中
list(APPEND EXTRA_INCLUDES "${PROJECT_SOURCE_DIR}/mathlib")
endif()
# 增加生成可执行文件,生成的程序名称为:tutorial_first
add_executable(tutorial src/tutorial.cpp)
# 对目标的外部库进行链接操作
target_link_libraries(tutorial PUBLIC ${EXTRA_LIBS})
# 为指定项目添加 include 路径
target_include_directories(tutorial PUBLIC
"${PROJECT_BINARY_DIR}"
${EXTRA_INCLUDES}
)
mathlib路径下CMakeLists.txt文件为:
代码语言:javascript
复制
# 设置动态库的版本 为1.2
SET_TARGET_PROPERTIES(mathlib PROPERTIES VERSION 1.2 SOVERSION 1)
# 为库mathlib 添加源文件,该命令声明库文件
add_library(mathlib mathlib.cpp)
为了将cmake中的变量自动传递到程序中,在TutorialConfig.h.in中添加#cmakedefine USE_MYMATH命令用于在cmake中生成USE_MYMATH宏定义。 TutorialConfig.h.in中代码为:
代码语言:javascript
复制
// the configured options and settings for Tutorial
#define Tutorial_VERSION_MAJOR @tutorial_second_VERSION_MAJOR@
#define Tutorial_VERSION_MINOR @tutorial_second_VERSION_MINOR@
#cmakedefine USE_MYMATH
在程序tutorial.cpp中添加处理命令:在cmake中定义USE_MYMATH的时候在程序中才会编译该命令块。具体请看CMakeDemo4代码。
代码语言:javascript
复制
#ifdef USE_MYMATH
# include "MathFunctions.h"
#endif
命令使用:
set_target_properties:设置目标的属性值
代码语言:javascript
复制
set_target_properties(target1 target2 ...
PROPERTIES prop1 value1
prop2 value2 ...)
add_library: 为生成的库添加源文件,是库的名字,直接写名字即可,不要写lib,会自动加上前缀。STATIC表示静态库(lib),SHARED表示动态库(so)。
代码语言:javascript
复制
add_library(<name> [STATIC | SHARED | MODULE]
[EXCLUDE_FROM_ALL]
source1 [source2 ...])
option: 提供一个选项是OFF或者ON,如果没有初始值被提供则默认使用OFF。
代码语言:javascript
复制
option(<option_variable> "help string describing option"
[initial value])
add_subdirectory: 添加一个编译的子路径,在子路径中查找CMakeLists.txt文件,并进行编译。
代码语言:javascript
复制
add_subdirectory(source_dir [binary_dir]
[EXCLUDE_FROM_ALL])
list:对项目中的所有值构建一个list,然后对变量进行操作。
代码语言:javascript
复制
list(LENGTH <list> <output variable>)
list(GET <list> <element index> [<element index> ...]
<output variable>)
list(APPEND <list> [<element> ...])
list(FILTER <list> <INCLUDE|EXCLUDE> REGEX <regular_expression>)
list(FIND <list> <value> <output variable>)
list(INSERT <list> <element_index> <element> [<element> ...])
list(REMOVE_ITEM <list> <value> [<value> ...])
list(REMOVE_AT <list> <index> [<index> ...])
list(REMOVE_DUPLICATES <list>)
list(REVERSE <list>)
list(SORT <list>)
target_link_libraries:对目标进行链接操作,如果有需要链接的库文件的时候才进行操作,如果该项目没有库文件,则不需要该命令。该命令一般在add_executable后面。
代码语言:javascript
复制
target_link_libraries(<target> ... <item>... ...)
CMake在生成文件的过程中会生成很多中间缓存文件,为了使项目更简洁,文件路径更清楚,一般会在项目的root目录下建立一个文件夹,用于存储CMake生成的中间文件。而一般使用的文件家名称为build或者release。下面是使用命令:
代码语言:javascript
复制
# 进入项目的root目录,本文为:tutorial_first
cd tutorial_first
# 创建存储缓存文件的文件夹,build
mkdir build
# 使用CMake命令生成makefile文件
cmake ..
# 使用make命令进行编译
cmake --build .
原网址: 访问
创建于: 2024-05-27 13:06:12
目录: default
标签: 无
未标明原创文章均为采集,版权归作者所有,转载无需和我联系,请注明原出处,南摩阿彌陀佛,知识,不只知道,要得到
java windows火焰图_mob64ca12ec8020的技术博客_51CTO博客 - 在windows下不可行,不知道作者是怎样搞的 监听SpringBoot 服务启动成功事件并打印信息_监听springboot启动完毕-CSDN博客 SpringBoot中就绪探针和存活探针_management.endpoint.health.probes.enabled-CSDN博客 u2u转换板 - 嘉立创EDA开源硬件平台 Spring Boot 项目的轻量级 HTTP 客户端 retrofit 框架,快来试试它!_Java精选-CSDN博客 手把手教你打造一套最牛的知识笔记管理系统! - 知乎 - 想法有重合-理论可参考 安宇雨 闲鱼 机械键盘 客制化 开贴记录 文本 linux 使用find命令查找包含某字符串的文件_beijihukk的博客-CSDN博客_find 查找字符串 ---- mac 也适用 安宇雨 打字音 记录集合 B站 bilibili 自行搭建 开坑 真正的客制化 安宇雨 黑苹果开坑 查找工具包maven pom 引用地 工具网站 Dantelis 介绍的玩轴入坑攻略 --- 关于轴的一些说法 --- 非官方 ---- 心得而已 --- 长期开坑更新 [本人问题][新开坑位]关于自动化测试的工具与平台应用 机械键盘 开团 网站记录 -- 能做一个收集的程序就好了 不过现在没时间 -- 信息大多是在群里发的 - 你要让垃圾佬 都去一个地方看难度也是很大的 精神支柱 [超级前台]sprinbboot maven superdesk-app 记录 [信息有用] [环境准备] [基本完成] [sebp/elk] 给已创建的Docker容器增加新的端口映射 - qq_30599553的博客 - CSDN博客 [正在研究] Elasticsearch, Logstash, Kibana (ELK) Docker image documentation elasticsearch centos 安装记录 及 启动手记 正式服务器 39 elasticsearch 问题合集 不断更新 6.1.1 | 6.5.1 两个版本 博客程序 - 测试 - bug记录 等等问题 laravel的启动过程解析 - lpfuture - 博客园 OAuth2 Server PHP 用 Laravel 搭建带 OAuth2 验证的 RESTful 服务 | Laravel China 社区 - 高品质的 Laravel 和 PHP 开发者社区 利用Laravel 搭建oauth2 API接口 附 Unauthenticated 解决办法 - 煮茶的博客 - SegmentFault 思否 使用 OAuth2-Server-php 搭建 OAuth2 Server - 午时的海 - 博客园 基于PHP构建OAuth 2.0 服务端 认证平台 - Endv - 博客园 Laravel 的 Artisan 命令行工具 Laravel 的文件系统和云存储功能集成 浅谈Chromium中的设计模式--终--Observer模式 浅谈Chromium中的设计模式--二--pre/post和Delegate模式 浅谈Chromium中的设计模式--一--Chromium中模块分层和进程模型 DeepMind 4 Hacking Yourself README.md update 20211011
Laravel China 简书 知乎 博客园 CSDN博客 开源中国 Go Further Ryan是菜鸟 | LNMP技术栈笔记 云栖社区-阿里云 Netflix技术博客 Techie Delight Linkedin技术博客 Dropbox技术博客 Facebook技术博客 淘宝中间件团队 美团技术博客 360技术博客 古巷博客 - 一个专注于分享的不正常博客 软件测试知识传播 - 测试窝 有赞技术团队 阮一峰 语雀 静觅丨崔庆才的个人博客 软件测试从业者综合能力提升 - isTester IBM Java 开发 使用开放 Java 生态系统开发现代应用程序 pengdai 一个强大的博主 HTML5资源教程 | 分享HTML5开发资源和开发教程 蘑菇博客 - 专注于技术分享的博客平台 个人博客-leapMie 流星007 CSDN博客 - 舍其小伙伴 稀土掘金 Go 技术论坛 | Golang / Go 语言中国知识社区
最新评论