缩小从int到long unsigned int {}的转换在C ++ 11中是不正确的

时间:2014-02-11 23:48:24

标签: c++ c c++11 gcc-warning gcc4.8

当我运行下面的代码时 - 我收到警告“缩小从int转换为long unsigned int inside {}在C ++ 11 [#Wnarrowing]中格式不正确。我正在使用GNU 4.8编译器。

typedef struct TableEntry
{
    unsigned long value;
    const char *label;
} TableEntry;

enum FunctionType
{
    NORMAL   = 0, 
    RANGE    = 1
};


TableEntry functionTypes[] = 
{
    {NORMAL,   "NORMAL"},
    {RANGE, "RANGE"}
};

我不明白为什么编译器将enum视为int?
这是GCC 4.8中的错误吗?有没有解决方法? 任何帮助表示赞赏。

4 个答案:

答案 0 :(得分:7)

如果可行的话:

enum FunctionType
{
    NORMAL   = 0, 
    RANGE    = 1
};

typedef struct TableEntry
{
    FunctionType value;
    const char *label;
} TableEntry;


TableEntry functionTypes[] = 
{
    {NORMAL,   "NORMAL"},
    {RANGE, "RANGE"}
};

否则,将结构中的类型更改为int,或者将枚举显式基于与结构中相同的类型。

顺便说一下,我认为g ++警告是没有根据的,错误的,因为原始代码是有效的C ++ 03。 更正:正如我现在所理解的那样,诊断是正确的,这是C ++ 11中的一个重大变化。我简直不敢相信。


关于命名约定:所有大写标识符都适用于Java程序员(习惯于该约定),但在C ++中,它们增加了无意中文本替换的可能性。还有审美方面的考虑因素。在为宏保留所有大写字母方面取得了很大的成功。

答案 1 :(得分:4)

通常底层类型的无范围枚举是int(它可以是任何可以表示枚举数的所有值的整数类型)。

但是我没有看到任何缩小转换,因为unsigned long类型可以表示int类型的所有值。

编辑:我似乎错了,因为我发现标准中的一个例子与我的假设相矛盾

unsigned int ui1 = {-1}; // error: narrows

因此无法使用包含负数的初始值设定项列表初始化unsigned int。

为避免警告,枚举可写为

enum FunctionType : unsigned int // or unsigned long
{
    NORMAL   = 0, 
    RANGE    = 1
};

答案 2 :(得分:2)

  • 您可以将“value”更改为int
  • 或者您可以使用强类型的新“枚举类”(c ++ 11),并将此“值”声明为此类型。

答案 3 :(得分:0)

由于你使用的是c ++ 11,你可以像这样声明你的枚举:
enum Enum2 : unsigned char;
这应该迫使枚举工作。也就是说,IDEONE对您发布的代码没有警告/错误。可能只是海湾合作委员会过分迂腐。