繁体   English   中英

C ++-枚举vs.常量vs.#定义

[英]C++ - enum vs. const vs. #define

在本文结尾处: http : //www.learncpp.com/cpp-tutorial/45-enumerated-types/ ,其中提到了以下内容:

最后,与常量变量一样,枚举类型将显示在调试器中, 在这方面它们比#defined值更有用

上面的黑体字如何实现?

谢谢。

考虑一下这段代码,

#define WIDTH 300

enum econst
{
   eWidth=300
};

const int Width=300;

struct sample{};

int main() 
{
        sample s;
        int x = eWidth * s; //error 1
        int y = WIDTH * s;  //error 2
        int z = Width * s;  //error 3
        return 0;
}

显然,每个乘法都会导致编译错误, 但是请查看GCC如何为每个乘法错误生成消息:

prog.cpp:19:错误:“ eWidth * s”中的“ operator *”不匹配
prog.cpp:20:错误:'300 * s'中的'operator *'不匹配
prog.cpp:21:错误:“宽度* s”中的“运算符*”不匹配

在错误消息中,您看不到已#defined的宏WIDTH ,对吗? 那是因为当GCC尝试编译对应于第二个错误的行时,它没有看到WIDTH ,只看到300,就像在GCC编译行之前一样,预处理器已经用300代替了WIDTH枚举 eWidthconst Width不会发生任何此类情况。

自己在此处查看错误: http : //www.ideone.com/naZ3P


另外,请阅读Item 2 : Prefer consts, enums, and inlines to #defines不是Scott Meyers的Effective C ++中的#define。

enum是带有调试信息的编译时间常数,没有存储分配。

const分配有一个存储,具体取决于编译器是否通过不断传播对其进行了优化。

#define没有存储分配。

#define值被预处理器替换为声明为它们的值,因此在调试器中,它仅看到该值,而不是#defined名称,例如,如果您具有#define NUMBER_OF_CATS 10,则在调试器中,您将看到只能看到10个(因为预处理器已用10替换了代码中的每个NUMBER_OF_CATS实例。

枚举类型本身就是一种类型,值是该类型的常量实例,因此预处理器将其保留下来,您将在调试器中看到该值的符号描述。

使用某些选项编译程序时,编译器会将枚举信息存储在二进制文件中。

当变量为枚举类型时,调试器可以显示枚举名称。 最好用示例显示:

enum E {
    ONE_E = 1,
};

int main(void)
{
    enum E e = 1;

    return 0;
}

如果使用gcc -g编译,则可以在gdb尝试以下方法:

Reading symbols from test...done.
(gdb) b main
Breakpoint 1 at 0x804839a: file test.c, line 8.
(gdb) run
Starting program: test 

Breakpoint 1, main () at test.c:7
7               enum E e = 1;
(gdb) next
9               return 0;
(gdb) print e
$1 = ONE_E
(gdb) 

如果使用了定义,则将没有适当的类型来赋予e ,而必须使用整数。 在这种情况下,编译器将打印1而不是ONE_E

-g标志要求gdb将调试信息添加到二进制文件中。 您甚至可以通过发出以下命令来查看它的存在:

xxd test | grep ONE_E

不过,我认为这不适用于所有架构。

至少对于我目前手头的Visual Studio 2008,这句话是正确的。 如果你有

#define X 3
enum MyEnum
{
    MyX = 3
};

int main(int argc, char* argv[])
{
    int i = X;
    int j = (int)MyX;
    return 0;
}

并且在main设置了一个中断点,可以将鼠标悬停在“ MyX”上,然后查看结果为3。如果将鼠标悬停在X上,看不到任何有用的东西。

但这不是语言属性,而是IDE行为。 下一版本和其他IDE可能会有所不同。 因此,只需检查一下您的IDE,看看这句话是否适用于您的情况。

我的回答太迟了,但是我觉得我可以添加一些内容-枚举vs. const vs. #define

枚举 -

  1. 不需要附加值(如果只想具有顺序值0、1、2 ..),而在#define的情况下,您需要手动管理可能会在某些时候导致人为错误的值
  2. 它的作用与在线调试期间可以在监视窗口中监视enum的值一样
  3. 您可以拥有一个枚举类型的变量,您可以为其分配一个枚举

    typedef枚举数字{DFAULT,CASE_TRUE,CASE_OTHER,};

    int main(void){数字number = CASE_TRUE; }

const-

  1. 它是常数,存储在内存的只读区域中,但可以使用地址来访问,这在#define情况下是不可能的
    1. 如果您使用const而不是#define,则您需要进行类型检查
  2. 例如,define是预处理指令,而const是编译时

    const char * name =“ vikas”;

您可以访问该名称并使用其基址来读取诸如vikas [3]来读取“ a”等。

#defines-是笨拙的预处理器指令,可进行文本替换

检查以下文章,不错的摘要http://www.queryhome.com/26340/define-vs-enum-vs-constant

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM