CMake-if()命令如何处理符号?作为字符串还是变量?

时间:2019-07-11 02:29:49

标签: cmake cmake-language

我不确定CMake if()命令会将条件子句中的符号视为变量还是字符串文字。所以我做了一些实验。

Script1.cmake

cmake_minimum_required(VERSION 3.15)

set(XXX "YYY") #<========== HERE!!

if(XXX STREQUAL "XXX")
    message("condition 1 is true") # If reach here, XXX is treated as string
elseif(XXX STREQUAL "YYY")
    message("condition 2 is true") # If reach here, XXX is treated as variable
endif()

输出为:

condition 2 is true

因此,我进入结论1

对于条件子句中的符号:

  • 如果符号以前被定义为变量,则CMake会将其视为变量并将其值用于评估。
  • 如果符号以前没有未定义作为变量,则CMake会将其从字面上视为字符串。

然后我做了另一个实验。

set(ON "OFF")
if(ON)
    message("condition 3 is true") # If reach here, ON is treated as a constant.
else()
    message("condition 4 is true") # If reach here. ON is treated as a variable.
endif()

输出为:

condition 3 is true

因此,尽管ON被明确地定义为变量,但if命令仍将其视为TRUE值常量。这直接与我之前的结论1 相矛盾。

那么我怎么知道CMake if()命令会将符号视为字符串还是变量?

ADD 1-11/11/04 AM 7/11/2019

似乎if(constant)形式在if()语句的其他形式之前。 (src

if(<constant>)
     

如果常数为1,ON,YES,TRUE,Y或非零数字,则为真。   如果常数为0,OFF,NO,FALSE,N,IGNORE,NOTFOUND,则返回False。   空字符串,或以后缀-NOTFOUND结尾。命名布尔常量   不区分大小写。 如果参数不是以下特定参数之一   常量,将其视为变量或字符串,以下   使用签名。

因此,现在,在应用我的结论1 之前,我必须先参考上述规则。 (这可能是一个答案,但我还不确定。)

1 个答案:

答案 0 :(得分:2)

欢迎来到CMake符号解释的荒野。

如果符号作为变量存在,则使用变量的值对表达式求值。否则,将改为评估变量的名称(或您所说的文字)。

如果添加${}序列,则行为会变得更加一致。然后,将变量的值每一次用于评估中。如果变量不存在或尚未分配值,则CMake使用多个占位符值评估为“假”。这些是您在文章的后半部分提到的价值观。

我相信这样做是为了向后兼容,CMake确实很擅长。对于CMake所做的大多数古怪的事情,通常都是以向后兼容的名义。

对于您在“ ON”变量中提到的不一致行为,这可能是由于CMake处理命令参数的优先级。我必须弄清楚,在符号查找发生之前就已经解析了常量。

因此,在了解/预测if语句的评估方式时,我最好的答案是经验。 CMake的源代码树和逻辑是一种宏伟,令人讨厌的野兽。

有人在讨论添加另一种语言(可能带有一种功能范例),但这是一项艰巨的任务。