CMake 从入门到崩溃3 - 基础语法之作用域

CMake 从入门到崩溃3 - 基础语法之作用域

上一篇我们介绍了 CMake 变量的使用,在这篇里我们会讲解 CMake 是怎样做名字查找的,也就是 CMake 中的变量作用域,由于 CMake 的作用域和其他编程语言区别很大,因此理解 CMake 作用域机制对正确的写出 CMake 脚本帮助很大

CMake 本质上是一个基于目录的作用域,设置一个变量,将为该文件和它的全部子目录设置该变量

CMake 中的名字查找沿作用域树向上做查找,因此你在子目录中修改了变量的值,只会影响到子目录及更深的目录,并不会对父目录产生任何影响

  • CMake 如果在当前作用域找不到该变量,就会到 Cache 中去找

🔑 条件语句和循环语句都不会引入新的作用域,这点和大多数编程语言都不同

set 命令提供了两个作用域相关的选项:

  • PARENT_SCOPE 将在父作用域而不是当前作用域设置该变量
  • CACHE 会将该变量写到 CMakeCache 中,set 的结果在所有作用域中都有效

子 CMake 脚本的作用域:

  • add_subdirectory 会引入新的作用域
  • include 在原有作用域中执行
    • 执行 set()unset() 影响的是调用者的作用域

除了基于目录的作用域外,CMake 函数还有自己的作用域,这意味着在函数中设置变量不会渗透到父作用域中,但对宏来说不是这样,因此我们更倾向于使用函数而不是宏

add_subdirectory

add_subdirectory(source_dir [binary_dir])

add_subdirectory 添加一个用于构建的子目录

source_dir

source_dir 通常是相对于当前目录的相对路径,但也可以指定它为绝对路径

CMake 将首先去执行 source_dir 目录下的 CMakeLists.txt,结束后再转回当前命令的下一行继续执行

调用 add_subdirectory 将导致在源码树中建立一个新结点,可以通过 CMAKE_CURRENT_SOURCE_DIR 获取到当前处理结点的完整路径

binary_dir

选项 binary_dir 用于指定子目录的输出应该放置在哪里,通常是相对于当前输出目录的相对路径,但也可以指定它为绝对路径

  • 典型的用法是,不去指定 binary_dir,未展开为绝对路径的 source_dir 的值将被用作 binary_dir
  • 调用 add_subdirectory 后,构建树中往往也会增加一个新结点,如果我们从来不指定 binary_dir 选项,源码树和构建树的结构应该是相同的
  • 这里说的输出包含 CMake 生成的构建系统文件和各种临时文件,如果仅仅想要改变目标生成的位置,比如二进制或库文件,应该通过 set_target_properties 命令改变对应目标的 *_OUTPUT_DIRECTORY 属性
posted @ 2022-02-27 21:10  路过的摸鱼侠  阅读(445)  评论(0编辑  收藏  举报