为什么 sizeof(0xF) 是 4 个字节?
why sizeof(0xF) is 4 bytes?
我有以下代码,
unsigned short code = 0x12E0;
code = code & 0x0FFF;
在我的 CLion IDE 中,我收到一条警告
"Values of type int
may not fit into the receiver type unsigned short
"
如果我把它写成 code &= 0x0FFF;
,警告就消失了。
为什么把0x0FFF
当成int
? sizeof(0xF)
是 4
,谁能解释为什么?
因为整数常量的类型被确定为第一个可以包含它的类型,而 short 根本不在类型列表中。 int
是第一个适合的类型。
引用 N1570/6.4.4.1p5:
The type of an integer constant is the first of the corresponding list in which its value can be represented.
Suffix | Decimal Constant | Octal or Hexadecimal Constant
------ | ---------------- | -----------------------------
none | int | int
| long int | unsigned int
| long long int | long int
| | unsigned long int
| | long long int
| | unsigned long long int
table明确指定int为第一种类型,而不是short
。
没有附加任何特定的后缀,像 0x12E0
或 0x0FFF
这样的整数常量是 int
类型。由于 0x
.
的前缀,它们将被归类为 "hexadecimal constant"
此外,如 中所述,对于没有显式后缀的整数常量(具体来说,“八进制或十六进制常量”),类型将根据以下列表
中排名最低的排名类型决定
int
unsigned int
long int
unsigned long int
long long int
unsigned long long int
可以容纳(代表)的值。
此外,出于这个原因,sizeof(0xF)
与 sizeof(int)
相同,后者恰好在您的平台中产生 4
的结果。
整数常量 0x0FFF
与所有整数常量一样,至少是 int
类型。不过这里没关系。
在表达式 code & 0x0FFF
中,操作数 code
和 0x0FFF
都受隐式整数提升的约束,整数提升规则。这适用于 小整数类型 ,例如 short
。所以 code
操作数总是被提升为(至少) int
而不管其他操作数的类型。
因此,如果您这样做,您将遇到同样的问题:
unsigned short code = 0x12E0;
unsigned short x = 0x0FFF;
code = code & x;
编译器可能会抑制前两行中的警告,因为它只是简单的赋值。但在最后一行有一个更复杂的表达式,整数溢出可能是一个问题。总的来说,编译器往往与这些警告不一致,因为它们不是强制性的。
迂腐但 100% 安全的代码,没有隐式类型转换,看起来像这样:
code = (unsigned short) ((unsigned int)code & 0x0FFFu);
我有以下代码,
unsigned short code = 0x12E0;
code = code & 0x0FFF;
在我的 CLion IDE 中,我收到一条警告
"Values of type
int
may not fit into the receiver typeunsigned short
"
如果我把它写成 code &= 0x0FFF;
,警告就消失了。
为什么把0x0FFF
当成int
? sizeof(0xF)
是 4
,谁能解释为什么?
因为整数常量的类型被确定为第一个可以包含它的类型,而 short 根本不在类型列表中。 int
是第一个适合的类型。
引用 N1570/6.4.4.1p5:
The type of an integer constant is the first of the corresponding list in which its value can be represented.
Suffix | Decimal Constant | Octal or Hexadecimal Constant ------ | ---------------- | ----------------------------- none | int | int | long int | unsigned int | long long int | long int | | unsigned long int | | long long int | | unsigned long long int
table明确指定int为第一种类型,而不是short
。
没有附加任何特定的后缀,像 0x12E0
或 0x0FFF
这样的整数常量是 int
类型。由于 0x
.
此外,如
int
unsigned int
long int
unsigned long int
long long int
unsigned long long int
可以容纳(代表)的值。
此外,出于这个原因,sizeof(0xF)
与 sizeof(int)
相同,后者恰好在您的平台中产生 4
的结果。
整数常量 0x0FFF
与所有整数常量一样,至少是 int
类型。不过这里没关系。
在表达式 code & 0x0FFF
中,操作数 code
和 0x0FFF
都受隐式整数提升的约束,整数提升规则。这适用于 小整数类型 ,例如 short
。所以 code
操作数总是被提升为(至少) int
而不管其他操作数的类型。
因此,如果您这样做,您将遇到同样的问题:
unsigned short code = 0x12E0;
unsigned short x = 0x0FFF;
code = code & x;
编译器可能会抑制前两行中的警告,因为它只是简单的赋值。但在最后一行有一个更复杂的表达式,整数溢出可能是一个问题。总的来说,编译器往往与这些警告不一致,因为它们不是强制性的。
迂腐但 100% 安全的代码,没有隐式类型转换,看起来像这样:
code = (unsigned short) ((unsigned int)code & 0x0FFFu);