1

我的你好.txt

cmake_policy(SET CMP0054 NEW)

set(VAR ON)

# VAR will be treated as a string
if("VAR")
  message(TRUE)
else()
  message(FALSE)
endif()

# output prints FALSE

从策略 CMP0054:

为了防止歧义,可以在带引号的参数或括号参数中指定潜在的变量或关键字名称。带引号或括号的变量或关键字将被解释为字符串,不会被取消引用或解释。请参阅政策 CMP0054。

CMake 文档没有提到if(<string>)

if(<variable|string>)

如果给定一个定义为非假常量的值的变量,则为真。否则为假。(注意宏参数不是变量。)

为什么非空字符串评估为FALSE

4

1 回答 1

1

您正在文档中查找正确的位置:

if(<variable|string>)

如果给定一个定义为非假常量的值的变量,则为真。否则为假。(注意宏参数不是变量。)

但是,文档并不完整,因为<string>没有明确提及该案例。仅包含字符串的 CMake if 语句的行为与此处描述的变量不同字符串的文档应为:

如果给定的字符串与真正的常量(1ONYESTRUEY或非零数)匹配,则为真。否则为假。

换句话说,任何与这些 CMake true 常量之一不匹配的字符串都将评估为 False。正如您已经指出的那样,字符串"VAR"

if ("VAR")
  message(TRUE)
else()
  message(FALSE)
endif()

打印FALSE。但是,作为字符串的真正常量(比如说"y"):

if ("y")
  message(TRUE)
else()
  message(FALSE)
endif()

打印TRUE

这个逻辑在 CMake源代码中的一个函数中是可验证的GetBooleanValue()

bool cmConditionEvaluator::GetBooleanValue(
  cmExpandedCommandArgument& arg) const
{
  // Check basic constants.
  if (arg == "0") {
    return false;
  }
  if (arg == "1") {
    return true;
  }

  // Check named constants.
  if (cmIsOn(arg.GetValue())) {
    return true;
  }
  if (cmIsOff(arg.GetValue())) {
    return false;
  }

  // Check for numbers.
  if (!arg.empty()) {
    char* end;
    double d = strtod(arg.c_str(), &end);
    if (*end == '\0') {
      // The whole string is a number.  Use C conversion to bool.
      return static_cast<bool>(d);
    }
  }

  // Check definition.
  const char* def = this->GetDefinitionIfUnquoted(arg);
  return !cmIsOff(def);
}
于 2019-12-23T15:44:31.217 回答