数据表示基础:补码
几乎所有计算机都完全使用二进制。这意味着它们只使用 0 和 1,而且计算机没有 - 或 + 符号。计算机必须以不同的方式表示负数。
我们可以通过将最高有效位 (MSB) 设置为 **符号位** 来表示二进制中的负数,符号位将告诉我们数字是正数还是负数。8 位数字的列标题将如下所示
-128 | 64 | 32 | 16 | 8 | 4 | 2 | 1 |
---|---|---|---|---|---|---|---|
MSB | LSB | ||||||
1 | 0 | 1 | 1 | 1 | 1 | 0 | 1 |
这里,最高有效位是负数,其他位是正数。您从 -128 开始,像往常一样添加其他位。上面的例子是十进制的 -67,因为:(-128 + 32 + 16 + 8 + 4 + 1 = -67)
-1 的二进制表示是 11111111。
请注意,只有在数字被指定为 **有符号** 的情况下,您才将最高有效位用作符号位。如果数字是 **无符号** 的,则无论它是 1 还是 0,msb 都是正数。
有符号二进制数 如果 MSB 为 0,则数字为正,如果为 1,则数字为负。 0000 0101 (positive) 1111 1011 (negative) |
方法:将负十进制数转换为二进制补码 假设您想将 **-35** 转换为二进制补码。首先,找到 35(正数)的二进制等效值 32 16 8 4 2 1 1 0 0 0 1 1 现在在 MSB 之前添加一个额外的位,将其设置为 0,得到 64 32 16 8 4 2 1 0 1 0 0 0 1 1 现在将所有位“翻转”:如果它是 0,将其改为 1;如果它是 1,将其改为 0 64 32 16 8 4 2 1 1 0 1 1 1 0 0 这个新的位表示 -64(负 64)。现在 **加 1** 64 32 16 8 4 2 1 1 0 1 1 1 0 0 + 1 1 0 1 1 1 0 1 如果我们执行一个快速的二进制 -> 十进制转换,我们得到:-64 + 16 + 8 + 4 + 1 = -64 + 29 = **-35** |
要找出补码数字的值,我们首先必须注意其符号位(最高有效位,最左边的位),如果该位是 0,我们像往常一样计算数字,如果该位是 1,则我们正在处理负数,需要找到它的值。
方法 1:将补码转换为十进制 要找到负数的值,我们必须找到并保留最右边的 1 及其右侧的所有位,然后将左侧的所有位翻转。以下是一个示例 1111 1011 note the number is negative 1111 1011 find the right most one 1111 1011 0000 0101 flip all the bits to its left 现在我们可以计算出这个新数字的值,它是 128 64 32 16 8 4 2 1 0 0 0 0 0 1 0 1 4 + 1 = −5 (remember the sign you worked out earlier!) |
方法 2:将补码转换为十进制 要找到负数的值,我们必须取 MSB 并对其应用一个负值。然后我们可以将所有标题值加在一起 1111 1011 note the number is negative -128 64 32 16 8 4 2 1 1 1 1 1 1 0 1 1 -128 +64 +32 +16 +8 +2 +1 = -5 |
如何处理更复杂的例子?
方法 1:将补码转换为十进制 1111 1100 note the number is negative 1111 1100 find the right most one 1111 1100 0000 0100 flip all the bits to its left 128 64 32 16 8 4 2 1 0 0 0 0 0 1 0 0 4 = −4 (remember the sign you worked out earlier!) |
方法 2:将补码转换为十进制 要找到负数的值,我们必须取 MSB 并对其应用一个负值。然后我们可以将所有标题值加在一起 1111 1100 note the number is negative -128 64 32 16 8 4 2 1 1 1 1 1 1 1 0 0 -128 +64 +32 +16 +8 +4 = -4 |
因此我们知道如何计算出给定负数的值。我们如何计算正数的负数版本?像这样,就是这样……
方法 1:将补码转换为二进制 取正数的二进制版本 0000 0101 (5) 0000 0101 find the right most one 0000 0101 1111 1011 flip all the bits to its left 现在我们可以看到正数和负数之间的区别 0000 0101 (5) 1111 1011 (−5) |
方法 2:将补码转换为二进制 取正数的二进制版本 从 -128 开始,我们知道 MSB 值得 -128。我们需要从这个数字开始往回计算 -128 64 32 16 8 4 2 1 1 1 1 1 1 0 1 0 -128 +64 +32 +16 +8 +1 = -5 0000 0101 (5) 1111 1011 (−5) |
练习:补码数字
0001 1011 答案 (正数)27 1111 1111 答案 (负数)0000 0001 = -1 0111 1101 答案 (正数)125 1001 1001 答案 (负数)0110 0111 = -103 1011 1000 答案 (负数)0100 1000 = -72 81(十六进制) 答案 (每个 HEX 字符使用 4 位)1000 0001(负数)-> 0111 1111 = -127 A8(十六进制) 答案 (每个 HEX 字符使用 4 位)1010 1000(负数)-> 0101 1000 = -88 将以下数字转换为以二进制表示的负数 0000 0001 答案 1111 1111 0110 0000 答案 1010 0000 0111 1111 答案 1000 0001 12(十进制) 答案 0000 1100 = +12 -> 1111 0100 = -12 67(十进制) 答案 0100 0011 = +67 -> 1011 1101 = -67 34 答案 0010 0010 = +34 -> 1101 1110 = -34 34(十六进制) 答案 (每个 HEX 字符使用 4 位)0011 0100 = +52 -> 1100 1100 = -54 7E(十六进制) 答案 (每个 HEX 字符使用 4 位)0111 1110 = +126 -> 1000 0010 = -126 |
如果 msb 用于提供负值,则最大可能值将受到限制。可能值的数目保持不变,这些数字的范围将包括负值以及正值。
使用补码表示的 个二进制位的范围
规则 | ||
最小值 = 例如,对于 3 位: |
规则 | ||
最大值 = 例如,对于 3 位: |
示例:二进制减法 在二进制中,从一个数减去另一个数时,事情可能会变得非常混乱。 X (82 denary) 0101 0010 Y (78 denary) 0100 1110 − 从 X 中减去 Y 的一种更简单的方法是将 Y 的负值加到 X 的值上。 X−Y = X+(−Y) 为此,我们首先需要找到 Y(十进制 78)的负值。 0100 1110 find the right most one 0100 1110 1011 0010 flip all the bits to its left 现在再次尝试求和。 0101 0010 X( 82 denary) 1011 0010 + Y(−78 denary) 0000 0100 (¹)¹¹¹ ¹ the one carried over the bit 9 is ignored 结果是 128 64 32 16 8 4 2 1 0 0 0 0 0 1 0 0 4 = 4 = 82-78 |
练习:二进制减法 找出以下二进制和的答案,并展示你的计算过程。 0110 1100 (108) - 0000 0111 (7) 答案 将 0000 0111 转换为负数 1111 1001 = -7 将这两个数加在一起。 0110 1100 + 1111 1001 0110 0101 = 101 (¹)¹¹¹¹ the one carried over the bit 9 is ignored 0001 1111 (31) - 0001 0011 (19) 答案 将 0001 0011 转换为负数 1110 1101 = -19 将这两个数加在一起。 0001 1111 + 1110 1101 0000 1100 = 12 (¹)¹¹¹¹ ¹¹¹ the one carried over the bit 9 is ignored 0111 0111 (119) - 0101 1011 (91) 答案 将 0101 1011 转换为负数 1010 0101 = -91 将这两个数加在一起。 0111 0111 + 1010 0101 0001 1100 = 28 (¹)¹¹ ¹¹¹ the one carried over the bit 9 is ignored 23 (hex) - 1F (hex) 答案 将十六进制值转换为二进制。 0010 0011 + 1110 0001 0000 0100 = 4 (¹)¹¹¹ ¹¹ the one carried over the bit 9 is ignored 0001 0010 (10) - 1110 0001 (-31) 答案 他们试图欺骗你。负数减去负数是什么? X - (-Y) = X + Y 0001 0010 (10) + 0001 1111 (31) 0011 0001 = 49 (¹) ¹¹ ¹¹ the one carried over the bit 9 is ignored |