【问题标题】:Is it legal to use #elif with #ifdef?将#elif 与#ifdef 一起使用是否合法?
【发布时间】:2018-04-13 05:25:16
【问题描述】:

Google 无法帮助我解决的一个简单问题。在 C++ 中在 #ifdef 的上下文中使用 #elif 子句是否合法?它似乎可以在 c++11 模式下(MSVC 2015/2017、clang、GCC)中的所有主要编译器按预期编译和工作,但我不确定它是否符合标准。

【问题讨论】:

  • 是的,这是合法的预处理器说话。 if 之后的 else-if。但是,尽量不要过分依赖预处理器的魔法。
  • #elif 可以与#ifdef、#ifndef 和#if 同等使用
  • @RemyLebeau 是的,我们可以将#ifdef 与#elif 一起使用。但是,如果我们 #define 宏的值为 0 用于 #ifdef 案例,#ifdef 案例将其测试为真。否则,如果我们将 #define 宏的值 0 用于 #elif 案例,则 #elif 案例将其测试为 false。
  • @jinbeomhong 那是因为#ifdef 测试宏的存在,而不是它的值。而#elif 测试宏的值
  • @RemyLebeau 这就是我正在寻找的答案。我知道我可以使用#ifdef #elif,但我想知道#elif 的含义是否会在这种情况下发生变化。

标签: c++ c-preprocessor preprocessor preprocessor-directive


【解决方案1】:

是的,语法允许在前面加上#elif,匹配#if、#ifdef 或#ifndef:

if-section:
if-group elif-groupsoptelse-groupoptendif -线

如果组:
# if 常量表达式 换行 组opt
# ifdef 标识符 换行 组opt
# ifndef 标识符 换行 组opt

请注意,#ifdef(X) 是 #if defined(X) 的缩写,#ifndef(X) 是 #if ! defined(X) 的缩写。

【讨论】:

    【解决方案2】:

    是的,这是允许的。

    语法是:

    if-group elif-groupsopt else-groupopt endif-line

    if-group的定义不仅包括#if,还包括#ifdef和#ifndef,所以#ifdef ... #elif ... #endif就可以了。

    【讨论】:

      【解决方案3】:

      对我来说,这个问题最重要的一点其实是rosshjb问题下的评论:

      @RemyLebeau 是的,我们可以将#ifdef 与#elif 一起使用。但是,如果我们为#ifdef case 使用值为0 的#define 宏,#ifdef case 会将其测试为真。否则,如果我们为#elif case 设置值为0 的#define 宏,则#elif case 将其测试为false。 – 20 年 1 月 19 日 19:40

      所以如果你有这样的块:

      #ifdef __linux__
        <some Linux code here>
      #elif _WIN32
        <some Windows code here>
      #endif
      

      那么第二个测试与第一个明显不同——第一个是检查__linux__ 是否被定义,第二个是检查符号_WIN32 的计算结果是否为真。在许多情况下,它的行为是相同的,但不能保证这样做。

      完整的等价物实际上是:

      #ifdef __linux__
        <some Linux code here>
      #elif defined(_WIN32)
        <some Windows code here>
      #endif
      

      这对每个人来说可能并不明显。

      使用Kerrick SB的答案,你也可以写出同样的#if语句:

      #if defined(__linux__)
        <some Linux code here>
      #elif defined(_WIN32)
        <some Windows code here>
      #endif
      

      这使得defined 对于#if 和#elif 更明显

      【讨论】:

      • 好点,感谢您强调这一点。我同意对于多个分支#if defined (...) 比简短形式#ifdef 好得多。
      • 感谢您提供的唯一正确答案。
      猜你喜欢
      • 1970-01-01
      • 2011-04-08
      • 2017-07-25
      • 2014-10-16
      • 2016-07-03
      • 2015-08-18
      • 1970-01-01
      • 1970-01-01
      • 2012-07-09
      相关资源
      最近更新 更多