类型的表示(二)
二、整数类型
无符号整数类型(unsigned char类型除外)对象表示的位可分为两组:值位(value bits)和填充位(padding bits)。填充位不是必需的。任何填充位的值都是未指定的。
用户可以访问无符号整数类型的填充位。如果一台机器使用一对16位的short(每个short都有自己的符号位。)组成一个32位的int,并且使用这样32位的int时会忽略低位short的符号位;作为32位的signed int,在确定值时会忽略一个填充位(在32位中间);但如果这个32位项作为32位的unsigned int时,该填充位对用户程序是可见的。
如果无符号整数类型存在N个值位,每个位表示l至2N-1之间2的不同幂,该类型对象能够使用纯二进制表示法(pure binary representation)表示0至2N-1之间的值,这称为值表示法(value representation)。以uint32_t类型为例,该类型32个值位,可表示的值域范围为[0,232-1]。
值位数量N称为无符号整数类型的宽度。bool类型存在一个值位和(sizeof(bool)*CHAR_BIT)-1个填充位;ISO/IEC 9899:2024标准不要求其它无符号整数类型存在任何填充位;无符号char类型不能存在任何填充位。
某些填充位组合可能会产生非值表示,例如:填充位是奇偶校验位(parity bit)。无论如何,有效值的算术运算都不会产生非值表示,除非是异常(例如:溢出)的一部分。填充位的所有其它组合都是值位指定值的替代对象表示(alternative object representations)。
有符号整数类型对象表示的位可分为三组:值位、填充位和符号位(sign bit)。填充位不是必需的,signed char类型中不应存在任何填充位。符号位只能是1个位。值位的每个位都应与对应无符号类型对象表示中的相同位具有相同的值(如果有符号类型中存在M个值位,对应无符号类型中存在N个值位,则M≤N)。如果符号位为0,不影响结果值;如果符号位为1,则应按以下列方式之一修改数值(以M等于7为例。):
-- 符号位对应值0将取反(原码)。
以-3为例,对应的无符号整数为3,二进制格式为0000 0011,符号位对应的0取反,二进制格式为1000 0011,该二进制格式原码解释为-3。
-- 符号位的值为-(2M)(补码)。
以-3为例,对应的无符号整数为3,二进制格式为0000 0011,符号位值为-27,所有位和为-125,二进制格式为1111 1101,该二进制格式补码解释为-3。
-- 符号位的值为-(2M-1)(反码)。
以-3为例,对应的无符号整数为3,二进制格式为0000 0011,符号位值为-(27-1),所有位和为-124,二进制格式为1111 1100,该二进制格式反码解释为-3。
注:计算机系统中有符号整数可以用三种不同的二进制编码方式表示:原码(sign-magnitude)、反码(ones' complement)和补码(two's complement)。ISO/IEC 9899:2024标准中有符号整数的编码方式是补码;ISO/IEC 9899:2018标准及更早标准中有符号整数的编码方式可以是原码、反码、补码。
原码和补码中符号位为1,所有值位为0的值,以及反码中符号位为1,所有值位为1的值,是非值表示还是正常值将由实现定义;对于原码和反码,如果上述值是正常值,则值为-0;例如:1000 0000(原码)、1111 1111(反码)。
如果实现支持-0,-0只能通过以下某种方式产生:
-- &、|、^、~、<<、>>运算符,其操作数产生-0。
-- +、-、*、/、%运算符,其中一个操作数是-0,并且结果为0。
-- 基于上述情况的复合赋值运算符。
上述情况实际生成的是-0,还是正常0,以及-0存储到对象中是否会转变成正常0,ISO/IEC 9899:2018标准未作明确说明。如果实现不支持-0,但&、|、^、~、<<、>>运算符的操作数产生-0,其行为是未定义的。
任何填充位的值都是未指定的。符号位为0的有符号整数类型的有效对象表示,也是相应无符号整数类型的有效对象表示,并且应该表示相同的值。对于任何整数类型,所有位都为0的对象表示应表示该类型中的0值。
整数类型的精度是值位的位数,不包括符号位和填充位;整数类型的宽度是值位和符号位的位数,不包括填充位。因此对于无符号整数类型,精度和宽度是相同的;对于有符号整数类型,宽度比精度大1。
主要参考资料:
3、wiki.sei.cmu.edu : Represent characters using an appropriate type
4、en.cppreference.com : Objects and alignment
6、baeldung.com : Calculating the Parity Bit of a Bit Sequence
7、open-std.org : Rationale for Internationa Standard - Programming Languages - C
9、cs.uaf.edu : One's Complement
10、cs.uaf.edu : Two's Complement