CMake 属性之目标属性

news/2024/10/8 20:19:56

【写在前面】

CMake 可以通过属性来存储信息。它就像是一个变量,但它被附加到一些其他的实体上,像是一个目录或者是一个目标。例如一个全局的属性可以是一个有用的非缓存的全局变量。

在 CMake 的众多属性中,目标属性 ( Target Properties ) 扮演着尤为重要的角色,它们直接关联到最终生成的可执行文件、库文件等构建产物。

更直观一点,如果把目标类比为 类 ( Class ),那么目标属性则类似 类成员 ( Class  Member )

class Target {string target_property;
};

【正文开始】

生成目标的方式有三种:

#生成可执行文件目标test
add_executable(test test.cpp)
#生成共享库目标test_lib
add_library(test_lib SHARED test.cpp)
#生成静态库目标test_lib
add_library(test_lib STATIC test.cpp)

定义目标属性:

给目标定义属性的命令为:

define_property(<GLOBAL | DIRECTORY | TARGET | SOURCE |TEST | VARIABLE | CACHED_VARIABLE>PROPERTY <name> [INHERITED][BRIEF_DOCS <brief-doc> [docs...]][FULL_DOCS <full-doc> [docs...]][INITIALIZE_FROM_VARIABLE <variable>])

在范围内定义一个属性,用于 set_property() 和 get_property() 命令。它主要用于定义属性的初始化或继承方式。从历史上看,该命令还将文档与属性相关联,但这不再被视为主要用例。

示例:

# 定义一个目标属性 TEST_TARGET,带有简短和详细描述 
define_property(TARGET PROPERTY TEST_TARGET BRIEF_DOCS "A test property"FULL_DOCS "A long description of this test property"
)

设置目标属性:

给目标设置属性的命令为:

set_property(<GLOBAL                      |DIRECTORY [<dir>]           |TARGET    [<target1> ...]   |SOURCE    [<src1> ...][DIRECTORY <dirs> ...][TARGET_DIRECTORY <targets> ...] |INSTALL   [<file1> ...]     |TEST      [<test1> ...]     |CACHE     [<entry1> ...]    >[APPEND] [APPEND_STRING]PROPERTY <name> [<value1> ...])

在范围的零个或多个对象上设置一个属性。

其中,有一个专用于设置目标属性命令:

set_target_properties(target1 target2 ...PROPERTIES prop1 value1prop2 value2 ...)

设置目标的属性。该命令的语法是列出您要更改的所有目标,然后提供您接下来要设置的值。您可以使用任何您想要的 prop 值对,稍后使用 get_property() 或 get_target_property() 命令提取它。

示例:

# 设置目标 TEST_TARGET 的属性 P_1 和 P_2 的值
set_target_properties(TEST_TARGET PROPERTIESP_1 "这是属性P_1的值"P_2 "这是属性P_2的值" 
)

获取目标属性:

获取目标的属性的命令为:

get_property(<variable><GLOBAL             |DIRECTORY [<dir>]  |TARGET    <target> |SOURCE    <source>[DIRECTORY <dir> | TARGET_DIRECTORY <target>] |INSTALL   <file>   |TEST      <test>   |CACHE     <entry>  |VARIABLE           >PROPERTY <name>[SET | DEFINED | BRIEF_DOCS | FULL_DOCS])

从范围内的一个对象获取一个属性。

其中,有一个专用于获取目标属性命令:

get_target_property(<VAR> target property)

从目标获取属性。属性的值存储在变量“”中。如果未找到目标属性,则行为取决于它是否已被定义为 INHERITED 属性(请参阅:command:define_property)。非继承属性会将<VAR>设置为<VAR>-NOTFOUND,而继承属性将搜索相关的父范围,如 define_property() 命令所述,如果仍然找不到属性 <VAR> 将被设置为空字符串。

使用 set_target_properties() 设置目标属性值。属性通常用于控制目标的构建方式,但有些属性会查询目标。此命令可以获得迄今为止创建的任何目标的属性。目标不需要位于当前的 CMakeLists.txt 文件中。

示例:

# 获取目标 TEST_TARGET 的属性 P_1 的值,并将其存储在变量 TEST_TARGET_P1 中
get_target_property(TEST_TARGET_P1 TEST_TARGET P_1) 

最后完整测试一遍:

# 要求 CMake 最低版本为 3.16
cmake_minimum_required(VERSION 3.16)# 定义项目名称为 PROPERTY_TEST,版本号为 1.0,使用 C++ 语言
project(PROPERTY_TEST VERSION 1.0 LANGUAGES CXX)# 添加一个名为 TEST_TARGET 的可执行文件,其源文件为 test.cpp
add_executable(TEST_TARGET test.cpp)# 定义一个目标属性 TEST_TARGET,带有简短和详细描述 
define_property(TARGET PROPERTY TEST_TARGET BRIEF_DOCS "A test property"FULL_DOCS "A long description of this test property"
)# 设置目标 TEST_TARGET 的属性 P_1 和 P_2 的值
set_target_properties(TEST_TARGET PROPERTIESP_1 "这是属性P_1的值"P_2 "这是属性P_2的值" 
)# 获取目标 TEST_TARGET 的属性 P_1 的值,并将其存储在变量 TEST_TARGET_P1 中
get_target_property(TEST_TARGET_P1 TEST_TARGET P_1) # 打印变量 TEST_TARGET_P1 的值
message("TEST_TARGET_P1: ${TEST_TARGET_P1}") 

CMake 输出如下:

image


【结语】

最后,属性在 CMake 中是可继承的。这意味着,如果一个目标继承了另一个目标的属性,那么它将自动获得父目标的属性值。这种继承关系在构建大型项目时非常有用,因为它减少了重复的配置。

CMake 的属性系统是一个强大的工具,它提供了细粒度的控制,允许我们定制构建过程。通过合理使用属性,我们可以创建更加灵活和可维护的构建系统。掌握属性的使用,是每个 CMake 用户进阶的必经之路,希望这篇文章能够帮助你更好地理解和使用 CMake 的属性系统。

项目链接(多多star呀..⭐_⭐):

Github 地址:https://github.com/mengps/LearnCMake

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.ryyt.cn/news/69137.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈,一经查实,立即删除!

相关文章

模板测试

模板测试(Stencil Test)是3D渲染中的一种技术,它根据预设条件比较参考值与模板缓冲区的值来决定片段是否进行下一步深度测试。本文介绍了模板测试的条件判断公式、语法,包括命令、比较函数,以及更新操作的各种关键字,如Keep、Zero等。并通过穿透效果的例子展示了模板测试…

CH57X/CH58X/CH59X 加PA应用

一、前言在有些时候产品需要做到更远的距离在原来的基础上加上PA放大芯片来实现广播或者连接距离上的提升。 PA是Power Amplifier的简称,中文名称为功率放大器,简称“功放”,指在给定失真率条件下,能产生最大功率输出以驱动某一负载的放大器。对于射频通信系统,PA负责发射通道…

csp-s 模拟 8

难度 ★★★★☆csp-s模拟8 T1 score and rank 特殊性质,题意转换 妙妙题 对于 \(S\) 小于等于 \(0\) 的情况答案显然是所有大于等于 \(S\) 的个数。 现在讨论 \(S\) 大于 \(0\) 的情况。 先对序列做一个前缀和,题目要求即是让所有值减去前缀最小值小于 \(S\) 考虑有一段连续…

C#联合Visionpro编程学习记录,视觉中需要考虑旋转中心工况的计算方法探讨

一、考虑旋转中心的工况解法, 1,视觉中引导定位或者对位贴合时,机械手或者xyzr轴上手爪中心和末端轴中心不同轴时,就要考虑旋转中心问题; 2,如果设备的CT要求没有很苛刻,可以采用2次拍照的方案解决,1次拍照后纠偏角度,然后在纠正角度后的位置2次拍照纠正x、y偏差;看下…

海外模组联网非常难?不往忘了APN配置…

​除了中国之外,国外的4G信号都比较差劲。 做海外的设备,如果忽视了射频的信号质量,肯定是要吃大亏的! 所以,海外模组的联网问题,会比国内要多不少。 客户在实际应用中或多或少都会遇到:网络相关问题:例如:连不上网,APN不会配置,APN没有配置,当地信号差… 软件升级…

轻松上云怎么操作?IoT_CLOUD之中移OneNET

​最近来了很多新朋友,也经常被问:可以多讲些云平台的操作吗?当然可以!文末留言你想要了解的云平台,优先安排~ 接下来,本文将以Air780E+LuatOS作为示例,教你使用合宙IoT_CLOUD连接中移OneNET物联网云平台。一、IoT_CLOUD简1.1 IoT_CLOUD特色简介 IoT_CLOUD——是合宙专门…

实验2 C语言分支与循环基础应用编程-1

任务一#include <stdio.h> #include <stdlib.h> #include <time.h> #define N 5 #define N1 397 #define N2 476 #define N3 21int main() {int cnt;int random_major, random_no;srand(time(NULL)); // 以当前系统时间作为随机种子cnt = 0;while(cnt &…