2

我正在编译在 Visual C++ 2012 中为 GCC 编写的代码。我收到了关于使用以下枚举截断枚举值的警告(由于值超出了 int 的范围):

enum tile_flags {
   TILE_FLAG_INNER_FLAME= 0x10000000ULL,
    TILE_FLAG_CONSTRICTED= 0x20000000ULL,

    TILE_FLAG_MIMIC_INEPT 0x2000000000ULL
    TILE_FLAG_MIMIC 0x4000000000ULL
    TILE_FLAG_MIMIC_RAVEN 0x6000000000ULL
    TILE_FLAG_MIMIC_MASK 0x6000000000ULL
}

在为 x86 编译时,似乎 MSVC 只是截断了枚举值以适应 32 位。但是,在 GCC 中不会发生截断。海湾合作委员会发生了什么?我怎样才能使这项工作适用于 MSVC?

4

2 回答 2

10

从 N3485,第 7.2/6 节:

对于基础类型不固定的枚举,基础类型是一个整数类型,可以表示枚举中定义的所有枚举值。如果没有整数类型可以表示所有枚举数值,则枚举格式错误。使用哪种整数类型作为基础类型由实现定义,除非基础类型不得大于 int,除非枚举数的值不能适合 int 或 unsigned int。如果 enumerator-list 为空,则基础类型就好像枚举有一个值为 0 的单个枚举器。

因此,如果 MSVC 有必要的long long支持,它无论如何都应该使它成为底层类型。既然它没有,你可以尝试一件事来哄它。

指定基础类型:

enum tile_flags : unsigned long long {
    ...
};
于 2013-05-14T17:44:46.167 回答
0

如果您需要的条目比 anunsigned long long所能获得的多,请尝试使用结构:

struct tile_flags {
   bool innerFlame : 1;
   bool constricted : 1;
   bool mimicInept : 1;
   bool mimic : 1;
   // etc
};

这使用了一个位域,这通常意味着这些值将被尽可能紧密地打包,虽然它可以使构造比传统的标志数字更难一些,但它是您最简单的选择,而不是sizeof unsigned long long位。

于 2013-05-14T18:09:38.810 回答