C++ 为什么在Windows stdint.h中未正确定义UINTX_C()宏?

C++ 为什么在Windows stdint.h中未正确定义UINTX_C()宏?,c++,macros,windows-7-x64,language-lawyer,C++,Macros,Windows 7 X64,Language Lawyer,在MVSC中,当I#include时,我最终得到以下UINTX_C和INTX_C宏的定义: #define INT8_C(x) (x) #define INT16_C(x) (x) #define INT32_C(x) ((x) + (INT32_MAX - INT32_MAX)) #define UINT8_C(x) (x) #define UINT16_C(x) (x) #define UINT32_C(x) ((x) + (UINT32_MAX - UINT32_MAX))

在MVSC中,当I
#include
时,我最终得到以下UINTX_C和INTX_C宏的定义:

#define INT8_C(x)   (x)
#define INT16_C(x)  (x)
#define INT32_C(x)  ((x) + (INT32_MAX - INT32_MAX))

#define UINT8_C(x)  (x)
#define UINT16_C(x) (x)
#define UINT32_C(x) ((x) + (UINT32_MAX - UINT32_MAX))

很明显,8位和16位宏只是在未修改的情况下通过常量,这并不完全执行它们设计的功能。Windows上是否有其他文件可用于获取正确的定义?

据我所知,它们的定义是正确的

宏将扩展为与指定类型(而不是指定类型)对应的整数常量表达式

<> P> C和C++都没有一个语法类型的整数常量表达式,比int IN/COD>更窄。它依赖于隐式转换将
int
表达式转换为所需的更窄类型

< C++ > C++标准中包含C标题的代码>代码> <代码>。最新的C++标准是指1999 C标准。我不确定三C99技术勘误的地位是关于C++的。 查看7.20.4p1:

以下类似于宏的函数扩展为整数常量 适用于初始化具有整数类型的对象 对应于
中定义的类型。每个宏名称 对应于7.20.1.2或7.20.1.5中的类似类型名称

在第3段中:

表达式的类型应与 根据转换的相应类型的表达式 整数促销

(增加重点)

例如,
int\u least8\u t
可能是
签名字符的typedef。如果是这样的话,有如下定义是有意义的(并且是一致的):

#define INT8_C(x)   (x)
N1570是2011年ISO C标准的草案。1999年的ISO C标准(C99)实际上在这方面存在缺陷。它在7.18.4.1p2中指出,例如,
INT8_C(
value
以指定的 值和类型
int\u least8\u t
。这在一般情况下是不可能的(没有编译器扩展),因为C对于小于
int
类型的整型常量没有语法(并且不能使用强制转换,因为结果必须在
#if
表达式中可用——尽管原始C99标准中没有这一要求)。作为对以下内容的响应,工程师对此进行了更正,即该类型是根据
整数促销。修正后的文本在C99的草案中,并在已发布的C11标准中。

C++中,您有:i88t、t16、t32、ut88t、utIn16t、utInt3t。你不需要macros@amchaconMSVC的C99支持是出了名的不完整。我敢打赌,这对他们来说是不值得的。STL确实说,除了VS2015预览版中的tgmath.h之外,C99标准库支持是完整的,所以我不确定如果该声明是准确的,这些保证是什么。@Mgetz,C99说“宏INTN_C(value)应扩展为与int_leastN_t类型对应的整数常量表达式。”。VS将
INT8\u C(5)
扩展为
int
,而
int\u t
signed char
,因此看起来不一致。据我所知,C++11为此引用了C99。@克里斯:在本文中,“对应于”并不意味着它是同一类型。C99标准中有一个错误,在N1256和C11中已更正。
int 8_C(5)
的类型是整数升级后的
int至少8_t
类型(即
int
)。这是必要的,因为对于小于
int
类型的整型常量没有语法。拥有一个定义为您引用的宏似乎并不特别合适useful@KyleL我想到了一个用法:
bool is_set(uint64_t var,int bit){return!!(var&(uint64_C(1))@KyleL:本身没有——但它是所有受支持宽度(8、16、32和64位,可能更多)的宏集合之一。有些但不是全部都是不可操作的。通过定义它们,程序员不必担心它们是如何定义的。那么,有没有一种方法可以为uint8\u t或uint16\u t定义一个常量,保证以可移植的方式具有这些特定类型?@KyleL:没有。为什么需要这样一个常量?一个类型为
int将通过任何赋值、初始化、参数传递或返回隐式转换。