`const int <variable>`不能出现在常量表达式</variable>中

时间:2014-03-11 07:13:56

标签: c++ static const

我有以下声明:

class Rm
{
public:
    //defined message types
    static const int HELLO;
}
我在cpp文件中的

const int Rm::HELLO = 1;

但是当我尝试在另一个类的方法中使用它时:

int
Rn::ProcessMessages()
{
    messagesIter iter = messages.begin();
    while(iter != messages.end())
    {
        switch(iter->first)
        {
            case Rm::HELLO:
                myID = iter->second;
                break;  
        }
    }
}

我明白了: 错误:'Rm :: HELLO'不能出现在常量表达式Rm :: HELLO:

我做错了什么?

2 个答案:

答案 0 :(得分:4)

成员变量是常量,但它不是编译时常量。为此,您需要在C ++ 11中引入的constexpr关键字:

class Rm
{
public:
    //defined message types
    static constexpr int HELLO = 1;
};

如果您没有支持C ++ 11的编译器,则可以改为使用枚举:

class Rm
{
public:
    //defined message types
    enum
    {
        HELLO = 1
    };
};

答案 1 :(得分:3)

为了在HELLO中使用switch值,此时编译器需要知道它。基本上,对于整数类型的成员常量,意味着在声明中提供初始化值。因此,而不是

static const int HELLO;

DO

static const int HELLO = -1;

尽管初始化程序仍然只是一个纯声明。如果您获取此地址,则需要单独的定义。只是不要拿地址。


以上适用于整数类型,但即使是double成员常量也不能以这种方式定义,原因不明。另一种方法是使用C ++ 11 constexpr,但此时限制了代码的可移植性。 C ++ 03非整数类型常量的替代方法包括

  • 使用命名空间级别常量,而不是成员。

  • 使用产生(引用)值的函数。

  • 在类模板中定义常量,从专业化派生您的类。


最后需要注意的是,在C ++中,请为保留所有大写名称,例如HELLO。这样,您可以减少不需要的名称冲突和文本替换,并且代码也变得更容易。即,在C ++中使用名称hello,或Hello,或...

所有大写都用在某些语言中,特别是Java和Python,作为常量名称的约定,主要是因为原始C常量必须表示为宏。

在这些语言中,除了作为眼睛之外,所有大写都没有任何不良影响,但C ++确实有一个预处理器。