我很难理解这个练习:
在二进制补码表示中,我们的itoa版本没有 处理最大的负数,即n的值等于 - (2 ^(wordsize-1))。解释为什么不。修改它以正确打印该值,无论它运行的机器如何。
以下是itoa最初的样子:
void reverse(char s[], int n)
{
int toSwap;
int end = n-1;
int begin = 0;
while(begin <= end) // Swap the array in place starting from both ends.
{
toSwap = s[begin];
s[begin] = s[end];
s[end] = toSwap;
--end;
++begin;
}
}
// Converts an integer to a character string.
void itoa(int n, char s[])
{
int i, sign;
if ((sign = n) < 0)
n = -n;
i = 0;
do
{
s[i++] = n % 10 + '0';
} while ((n /= 10) > 0);
if (sign < 0)
s[i++] = '-';
s[i] = '\0';
reverse(s, i);
}
我找到了这个答案,但我不明白这个解释: http://www.stevenscs.com/programs/KR/ $ progs的/ KR-EX3-04.html
因为一个单词可以容纳的最大负数的绝对值大于最大正数的绝对值,所以在iota中早期设置正数为负数的语句会破坏其值。
他们是否说负号由于符号而包含的位数多于没有符号的正数?为什么乘以-1会影响大负数的存储方式?
答案 0 :(得分:0)
问题是,如果n是最大的负数,当你做n = -n时你得到0,因为你不能代表一个大的正数。
解决方案可以是将正数保存在一个长整数中。
答案 1 :(得分:0)
在两个补码表示中,您可以表示的值范围是-2n-1
到2n-1-1
。因此,对于8位,您可以表示-128到127范围内的值。这是短语的含义,&#34;单词可容纳的最大负数大于最大的正数。&#34;
只用3位进行说明,使其更清晰:
Value Bits
----- ----
0 000
1 001
2 010
3 011
-4 100
-3 101
-2 110
-1 111
对于3位,我们无法在两个补码中表示正 4
,因此n = -n;
赢了#t给我们预期的结果 1 。这就是上述原始atoi
实施无法处理INT_MIN
的原因。
<小时/>