首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >为什么C预处理器认为枚举值相等?

为什么C预处理器认为枚举值相等?
EN

Stack Overflow用户
提问于 2016-01-08 20:27:39
回答 6查看 12.9K关注 0票数 61

为什么在AB不同的情况下,以下代码中的std::cout行仍然可以运行?

代码语言:javascript
复制
#include <iostream>

enum T { A = 1, B = 2 };
// #define A 1
// #define B 2

int main() {
#if (A == B)
    std::cout << A << B;
#endif
}

如果我使用#define (注释掉了),我不会得到我所期望的输出。

问题的原因:

我想为一些测试代码提供一个模式选择器,在这个模式选择器中,我可以通过注释/取消注释顶部的行来轻松地更改模式:

代码语言:javascript
复制
enum T { MODE_RGB = 1, MODE_GREY = 2, MODE_CMYK = 3 };
// #define MODE MODE_RGB
#define MODE MODE_GREY
// #define MODE MODE_CMYK

int main() {
#if (MODE == MODE_RGB)
    // do RGB stuff
#elif (MODE == MODE_GREY)
    // do greyscale stuff
#else
    // do CMYK stuff
#endif

    // some common code

    some_function(arg1, arg2,
#if (MODE == MODE_RGB)
        // RGB calculation for arg3,
#elif (MODE == MODE_GREY)
        // greyscale calculation for arg3,
#else
        // CMYK calculation for arg3,
#endif
        arg4, arg5);
}

我知道我可以使用数字值,例如

代码语言:javascript
复制
#define MODE 1 // RGB
...
#if (MODE == 1) // RGB

但这会降低代码的可读性。

有没有一个优雅的解决方案呢?

EN

回答 6

Stack Overflow用户

回答已采纳

发布于 2016-01-08 20:34:09

没有名为AB的宏,因此在您的#if行中,AB将被0替换,因此您实际上拥有:

代码语言:javascript
复制
enum T { A = 1, B = 2 };

int main() {
#if (0 == 0)
    std::cout << A << B;
#endif
}

在编译器了解您的enum之前,预处理器就会运行。预处理器只知道宏(#define)。

票数 124
EN

Stack Overflow用户

发布于 2016-01-08 20:31:55

这是因为预处理器在编译前工作。

由于枚举定义发生在编译时,因此A和B在预处理时都被定义为空(pp- 0),因此相等,因此输出语句包含在编译后的代码中。

当您使用#define时,它们在预处理时的定义不同,因此语句的计算结果为false。

关于你想要做什么的评论,你不需要使用预处理器#if来做这件事。您可以只使用标准if,因为MODEMODE_GREY (或MODE_RGBMODE_CMYK)都仍然是已定义的:

代码语言:javascript
复制
#include <iostream>

enum T { MODE_RGB = 1, MODE_GREY = 2, MODE_CMYK = 3 };

#define MODE MODE_GREY

int main()
{
    if( MODE == MODE_GREY )
        std::cout << "Grey mode" << std::endl;
    else if( MODE == MODE_RGB )
        std::cout << "RGB mode" << std::endl;
    else if( MODE == MODE_CMYK )
        std::cout << "CMYK mode" << std::endl;

    return 0;
}

只使用预处理器的另一个选项是@TripeHound correctly answered below

票数 45
EN

Stack Overflow用户

发布于 2016-01-08 20:34:07

在条件预处理器指令中,未定义宏的标识符被解释为值0。因此,由于您没有定义宏AB,因此它们都被认为是0,并且两个0彼此相等。

未定义(对于预处理器)标识符被视为0的原因是因为它允许在条件中使用未定义的宏,而不使用#ifdef

票数 24
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34677148

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档