有符号和无符号int有什么区别?
有符号和无符号int有什么区别?
Answers:
您可能已经知道,int
s在内部以二进制存储。通常,aint
包含32位,但是在某些环境中可能包含16或64位(甚至是不同的数字,通常但不一定是2的幂)。
但是对于此示例,让我们看一下4位整数。微小,但对说明有用。
由于这样的整数中有4位,因此可以假定16个值之一。16是2到4的幂,或者2乘以2乘以2乘以2。这些值是多少?答案取决于此整数是asigned int
还是a unsigned int
。使用unsigned int
,该值永远不会为负;没有与该值关联的符号。这是四位的16个可能的值unsigned int
:
bits value
0000 0
0001 1
0010 2
0011 3
0100 4
0101 5
0110 6
0111 7
1000 8
1001 9
1010 10
1011 11
1100 12
1101 13
1110 14
1111 15
...这是一个四位的16个可能的值signed int
:
bits value
0000 0
0001 1
0010 2
0011 3
0100 4
0101 5
0110 6
0111 7
1000 -8
1001 -7
1010 -6
1011 -5
1100 -4
1101 -3
1110 -2
1111 -1
如您所见,对于signed int
,最高有效位是1
当且仅当数字为负数时。因此,对于signed int
s来说,该位称为“符号位”。
(unsigned)(-1)
是unsigned
(与二进制表示形式无关)的最大可表示值,对于2的补码来说,这是微不足道的,但其他表示形式则不然。
int
和unsigned int
是两种不同的整数类型。(int
也可以称为signed int
或signed
;unsigned int
也可以称为unsigned
。)
顾名思义,它int
是有符号整数类型,并且unsigned int
是无符号整数类型。这意味着它int
可以表示负值,并且unsigned int
只能表示非负值。
C语言对这些类型的范围提出了一些要求。的范围int
必须至少为-32767
.. +32767
,并且该范围的unsigned int
必须至少0
.. 65535
。这意味着两种类型都必须至少为16位。在许多系统上,它们是32位,在某些系统上甚至是64位。int
由于大多数现代系统使用二进制补码表示法,因此通常具有额外的负值。
也许最重要的区别是有符号与无符号算术的行为。对于signed int
,溢出具有未定义的行为。对于unsigned int
,没有溢出;产生值超出类型范围的任何操作都会回绕,例如UINT_MAX + 1U == 0U
。
任何整数类型(有符号的或无符号的)都会对无限的数学整数集的子范围进行建模。只要您使用类型范围内的值,一切都将起作用。当您接近类型的下限或上限时,会遇到不连续的情况,并且您会得到意想不到的结果。对于有符号整数类型,仅在非常大的负值和正值(超过INT_MIN
和)时才会出现问题INT_MAX
。对于无符号整数类型,对于非常大的正值和零值会出现问题。这可能是错误的来源。例如,这是一个无限循环:
for (unsigned int i = 10; i >= 0; i --) [
printf("%u\n", i);
}
因为i
是始终大于或等于零; 这就是无符号类型的本质。(在循环内,当i
为零时,i--
将其值设置为UINT_MAX
。)
实际上,有两个区别:
cout
使用C ++或printf
C语言):无符号整数位表示形式由打印函数解释为非负整数。此代码可以使用排序条件来标识整数:
char a = 0;
a--;
if (0 < a)
printf("unsigned");
else
printf("signed");