有符号类型(可能)可以表示相应无符号类型可表示的所有数字。例如,如果 unsigned int 类型使用 31 个值位和 1 个填充位表示,而有符号 int 类型使用 31 个值位和无填充位表示。是否允许实现这样做?
该标准规定6.3.1.8 Usual arithmetic conversions
:
否则,对两个操作数都执行整数提升。然后将以下规则应用于提升的操作数: 如果两个操作数具有相同的类型,则不需要进一步转换。
否则,如果两个操作数都具有有符号整数类型或都具有无符号整数类型,则具有较小整数转换等级的类型的操作数将转换为具有较高等级的操作数的类型。
否则,如果无符号整数类型的操作数的等级大于或等于另一个操作数类型的等级,则将有符号整数类型的操作数转换为无符号整数类型的操作数的类型。
由于int
和unsigned int
具有相同的等级 ( 6.3.1.1 Boolean, characters, and integers
),int
将转换为unsigned int
,但不是相反:
— 任何无符号整数类型的等级应等于相应的有符号整数类型的等级,如果有的话。
以 为后缀的整数常量u
始终是无符号的(参见 中的表格6.4.4.1 Integer constants
)。
6.3.1.1 Boolean, characters, and integers
第 2 条还告诉我们:
可以在可以使用 int 或 unsigned int 的表达式中使用以下内容:
— 整数类型的对象或表达式,其整数转换等级小于 int 和 unsigned int 的等级。
— _Bool、int、signed int 或 unsigned int 类型的位域。
如果一个 int 可以表示原始类型的所有值,则将该值转换为 int;否则,它将转换为无符号整数。这些被称为整数促销。整数提升不会改变所有其他类型。
因此,不,实现不能合法地转换unsigned int
为int
,除非您通过强制转换或分配明确要求。
编辑:第 2 条6.3.1.1 Boolean, characters, and integers
内容如下:
— 整数类型的对象或表达式,其整数转换等级小于int 和 unsigned int 的等级。
(国际标准 ISO/IEC 9899 第二版 1999-12-01)
— 整数类型的对象或表达式,其整数转换等级小于或等于int 和 unsigned int 的等级。
(WG14/N1256 委员会草案 — 2007 年 9 月 7 日 ISO/IEC 9899:TC3)
— 具有整数类型(除 int 或 unsigned int 之外)的对象或表达式,其整数转换等级小于或等于int 和 unsigned int 的等级。
(N1548 委员会草案 — 2010 年 12 月 2 日 ISO/IEC 9899:201x,
N1570 委员会草案 — 2011 年 4 月 12 日 ISO/IEC 9899:201x)
只是为了好玩,C++11 的4.5 Integral promotions [conv.prom]
:
如果 int 可以表示源类型的所有值,则整数转换等级 (4.13) 小于 int 等级的除 bool、char16_t、char32_t 或 wchar_t 的整数类型的纯右值可以转换为 int 类型的纯右值; 否则,可以将源纯右值转换为 unsigned int 类型的纯右值。
(N3242=11-0012,
N3337 日期:2012-01-16,
国际标准 ISO/IEC 14882 第三版 2011-09-01)