由于非常具体的原因,我有一个这样的枚举:
typedef enum RSGameType
{
RSGameTypeUnknown = 0,
RSGameType1v1 = '1v1',
RSGameType2v2 = '2v2',
RSGameType3v3 = '3v3',
RSGameType4v4 = '4v4',
RSGameTypeCustom = 'Cust'
} RSGameType;
然而,Clang警告我每个项目的'多字符常数'除了'Cust'之外(因为我认为这是一个4字符常量)。
除了使用等效数字之外,还有正确的方法可以关闭这些警告吗?前置null('\x001v1'
)没有任何效果,但附加一个有效(但这是不合需要的,因为值不再准确)。
答案 0 :(得分:7)
多字符常量不可移植;它们的值是实现定义的。该语言甚至不保证'1v1'
和'2v2'
具有不同的值。这可能不是一个问题,但如果您需要在不同编译器编译的代码之间共享RSGameType
值,则可能会遇到麻烦。
我认为你已经意识到了这一切。
但这是一个不受实现定义行为影响的解决方案:
#define CHAR3(c0, c1, c2) (((c0)<<16) | ((c1)<<8) | (c2))
#define CHAR4(c0, c1, c2, c3) (((c0)<<24) | ((c1)<<16) | ((c2)<<8) | (c3))
typedef enum RSGameType
{
RSGameTypeUnknown = 0,
RSGameType1v1 = CHAR3('1', 'v', '1'),
RSGameType2v2 = CHAR3('2', 'v', '2'),
RSGameType3v3 = CHAR3('3', 'v', '3'),
RSGameType4v4 = CHAR3('4', 'v', '4'),
RSGameTypeCustom = CHAR4('C', 'u', 's', 't')
} RSGameType;
答案 1 :(得分:2)
使用标记-Wno-multichar
。还有-Wfour-char-constants
,默认情况下已禁用,这就是您没有看到它的原因。
答案 2 :(得分:0)
制作多字符常量可以做的另一件有趣的事情就是将固定宽度字符串作为一个整数,就像你想要制作的那样。例如:
typedef unsigned long uint32;
typedef unsigned long long uint64;
uint32 make4ByteUIntegerFromChars( const char *convert ) {
// check that strlen( convert ) == 4 if you like
return * (uint32 *) convert;
}
uint64 make8ByteUIntegerFromChars( const char *convert ) {
// check that strlen( convert ) == 8 if you like
return * (uint64 *) convert;
}