1081|1

66

帖子

0

TA的资源

一粒金砂(高级)

楼主
 

《Cmake构建实战》3 Cmake基础语法学习 [复制链接]

本帖最后由 maskmoo 于 2024-10-20 21:45 编辑

第3章主要描述Cmake的基本使用语法,结合书中的实例整理如下

CMake程序

cmake的文件类型包括CMakeList.txt文件和扩展名为.cmake的文件。其中CMakeList.txt是用于组织构建项目源文件的目录结构,.cmake文件可以作为脚本和模块两种类型。

目录(CMakeList.txt) 脚本(<script>.cmake) 模块 (<module>.cmake)
注释

主要分为单行注释和多行注释,其中多行注释本质上是单行注释+括号参数的组成形式

#单行注释

#[=[多行注释 ]=]


命令调用

message if for等


命令参数

引号参数

#包含换行
message("CMake
你好!")

#不包含换行

message("\
CMake\
您好!\
")

 

 

非引号参数 

message("x;y;z") # 引号参数
message(x y z) # 多个非引号参数
message(x;y;z) # 非引号参数

 

变量引用

set(var_a 您好)
set(var_b a)

message(${var_${var_b}})

 

转义字符 

cmake_minimum_required(VERSION 3.20)

set("a?b" "变量a?b")

# \? 转义为 ?
message(${a\?b})
message(今天是几号\?) 

# \n 转义为换行符,\t 转义为制表符,\! 转义为 !
message(回答:\n\t今天是1号\!)

set("a;b" "变量a;b")

# 非引号参数中 \; 转义为 ;,且不分隔变量
message(x;y\;z)
# 引号参数中 \; 不转义
message("x;y\;z")
# 变量引用中 \; 转义为 ;
message("${a\;b}")

 

括号参数

message([==[
abc
def
]==])

message([===[abc
def
]===])

message([===[
随便写终止方括号并不会导致文本结束,
因此右边这两个括号]]也会包括在原始文本中。
下一行中最后的括号也是原始文本的一部分,
因为等号的数量与起始括号不匹配。]==]
]===])

 

 

变量

预定义变量

message("CMake命令行:${CMAKE_COMMAND}")
message("OS:${CMAKE_HOST_SYSTEM_NAME}")

 

定义普通变量

需要注意的是变量的作用域

function(f)
    set(a "我是修改后的a")
    set(b "我是b")
    set(c "我是c" PARENT_SCOPE)
endfunction()

set(a "我是a")
f()

message("a: ${a}")
message("b: ${b}")
message("c: ${c}")

 
缓存变量

cmake_minimum_required(VERSION 3.20)
project(Notepad)

set(path_to_notepad "" CACHE FILEPATH "Path to notepad.exe")

# 下面的命令将会用记事本打开同一目录中的in.txt
execute_process(COMMAND "cmd" "/c" 
    ${path_to_notepad} ${CMAKE_CURRENT_LIST_DIR}/in.txt)

 

环境变量

message("main \$ENV{PATH}: $ENV{PATH}")

列表

定义列表变量

include(print_list.cmake)

set(a "a;b;c")
set(b a;b;c)
set(c a b c)

print_list(a) # 输出:a | b | c
print_list(b) # 输出:a | b | c
print_list(c) # 输出:a | b | c

 


控制结构

if while  foreach  break continue

 


条件语法 

常量条件

 

变量条件

cmake_minimum_required(VERSION 3.20)

set(on "OFF")

if(on)
    message("ON")
else()
    message("OFF")
endif()

if(${on})
    message("ON")
else()
    message("OFF")
endif()

 

字符串条件 

if(ABC)
else()
    message("ABC不是一个已定义的变量,因此条件为假")
endif()

set(a "XYZ")
set(b "0")
set(c "a-NOTFOUND")

if(a)
    message("a是一个变量,其值非假值常量,因此条件为真")
endif()

if(b)
else()
    message("b是一个变量,其值为假值常量,因此条件为假")
endif()

if(c)
else()
    message("c是一个变量,其值为假值常量,因此条件为假")
endif()

 

逻辑运算

cmake_minimum_required(VERSION 3.20)

if(NOT OFF)
    message("NOT OFF为真")
endif()

if(ON AND YES)
    message("ON AND YES为真")
endif()

if(TRUE AND NOTFOUND)
else()
    message("TRUE AND NOTFOUND为假")
endif()

if(A-NOTFOUND OR YES)
    message("A-NOTFOUND OR YES为真")
endif()

单参数条件

set(a 1)

if(DEFINED a)
    message("DEFINED a为真")
endif()

if(CACHE{b})
else()
    message("CACHE{b}为假")
endif()

if(COMMAND set)
    message("COMMAND set为真")
endif()

if(EXISTS "${CMAKE_CURRENT_LIST_DIR}/逻辑运算.cmake")
    message("EXISTS \"${CMAKE_CURRENT_LIST_DIR}/逻辑运算.cmake\"为真")
endif()

 

双参数条件

cmake_minimum_required(VERSION 3.20)

set(a 10)
set(b "abc")
set(list 1;10;100)

if(11 GREATER a)
    message("11 GREATER a为真")
endif()

if(1 LESS 2)
    message("1 LESS 2为真")
endif()

if(b STRLESS "b")
    message("b LESS \"b\"为真")
endif()

if(1.2.3 VERSION_LESS 1.10.1)
    message("1.2.3 LESS 1.10.1为真")
endif()

if(abc MATCHES a..)
    message("abc MATCHES a..为真")
endif()

if(ab MATCHES a..)
else()
    message("ab MATCHES a..为假")
endif()

if(a IN_LIST list)
    message("a IN_LIST list为真")
endif()

 

 

括号和条件优先级

cmake_minimum_required(VERSION 3.20)

if(NOT TRUE AND FALSE OR TRUE)
    message("NOT FALSE AND TRUE OR FALSE为真")
endif()

if(NOT (TRUE AND (FALSE OR TRUE)))
else()
    message("NOT FALSE AND TRUE OR FALSE为假")
endif()

  

变量展开

cmake_minimum_required(VERSION 3.20)

set(A FALSE)
set(B "A")

if(B)
    message("B为真")
endif()

if(${B})
else()
    message("\${B}为假")
endif()

while(NOT ${B})
    message("NOT \${B}为真")
    break()
endwhile()

 
命令定义

宏定义

macro(my_macro a b)
    set(result "参数a: ${a}, 参数b: ${b}")
endmacro()

my_macro(x y)
message("${result}") # 输出:参数a: x, 参数b: y

MY_macro(A;B)
message("${result}") # 输出:参数a: A, 参数b: B

MY_MACRO(你 好)
message("${result}") # 输出:参数a: 你, 参数b: 好

 

函数定义

function(my_func a b)
    set(result "参数a: ${a}, 参数b: ${b}" PARENT_SCOPE)
endfunction()

my_func(x y)
message("${result}") # 输出:参数a: x, 参数b: y

MY_func(A;B)
message("${result}") # 输出:参数a: A, 参数b: B

MY_FUNC(你 好)
message("${result}") # 输出:参数a: 你, 参数b: 好

 

 

参数访问   

macro(my_macro p)
    message("ARGC: ${ARGC}")
    message("ARGV: ${ARGV}")
    message("ARGN: ${ARGN}")
    message("ARGV0: ${ARGV0}, ARGV1: ${ARGV1}")
endmacro()

function(my_func p)
    message("ARGC: ${ARGC}")
    message("ARGV: ${ARGV}")
    message("ARGN: ${ARGN}")
    message("ARGV0: ${ARGV0}, ARGV1: ${ARGV1}")
endfunction()

my_macro(x y z)
my_func(x y z)

 

参数的设计与解析

function(my_copy_func)
    message("ARGN: ${ARGN}")

    set(options OVERWRITE MOVE)
    set(oneValueArgs DESTINATION)
    set(multiValueArgs PATHS)

    cmake_parse_arguments(
        my 
        "${options}" "${oneValueArgs}" "${multiValueArgs}"
        ${ARGN}
    )

    message("OVERWRITE:\t${my_OVERWRITE}")
    message("MOVE:\t\t${my_MOVE}")
    message("DESTINATION:\t${my_DESTINATION}")
    message("PATHS: \t\t${my_PATHS}")
    message("---")
endfunction()

my_copy_func(DESTINATION ".." PATHS "1.txt" "2.txt" OVERWRITE)
my_copy_func(MOVE DESTINATION "../.." PATHS "3.txt" "4.txt")
my_copy_func(DESTINATION "../folder;name" PATHS 1.txt;2.txt)

 

宏和函数参数的区别

macro(my_macro p)
    message("-- my_macro --")

    if(p)
        message("p为真")
    endif()

    set(i 1)
    message("ARGV i: ${ARGV${i}}")
endmacro()

function(my_func p)
    message("-- my_func --")

    if(p)
        message("p为真")
    endif()

    set(i 1)
    message("ARGV i: ${ARGV${i}}")
endfunction(my_func)

my_macro(ON x)
my_func(ON x)

 

最新回复

感谢楼主分享的cmake基本语法知识,内容详实,通俗易懂,受益匪浅   详情 回复 发表于 2024-10-21 14:27
点赞 关注

回复
举报

718

帖子

5

TA的资源

纯净的硅(高级)

沙发
 

感谢楼主分享的cmake基本语法知识,内容详实,通俗易懂,受益匪浅

 
 

回复
您需要登录后才可以回帖 登录 | 注册

随便看看
查找数据手册?

EEWorld Datasheet 技术支持

相关文章 更多>>
关闭
站长推荐上一条 1/10 下一条

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

About Us 关于我们 客户服务 联系方式 器件索引 网站地图 最新更新 手机版

站点相关: 国产芯 安防电子 汽车电子 手机便携 工业控制 家用电子 医疗电子 测试测量 网络通信 物联网

北京市海淀区中关村大街18号B座15层1530室 电话:(010)82350740 邮编:100190

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved
快速回复 返回顶部 返回列表