[音乐]
那么我们来看几个例子,假定这个机器数有n位
那么负的2的n-1次方它的补码 代到刚才的公式里面去就是
2的n次方这个模,加上x,就是加负的2的n-1次方
那么这个2的n次方实际上就是1后面有n个0 然后减去2的n-1次方
就是1后面有n个0
减掉1后面有
n-1个0,减下来的结果当然就是0,然后是1
那么这个最后的结果这儿有 n-1个0,这是1,所以最后的结果就是1
后面有n-1个0 那么机器数有n位就表示这个
模是n次方,模是n次方 那么我们来看第二个例子,-1的补码
-1的补码按照公式也是2的n次方减去1 那么2的n次方减1实际上就是很好算
2的n次方就相当于 1后面有n个0
减1,那很显然这边是1
一直是1 1,这边是0,所以最终应该是得到n个1
iii,那么0的补码 不管是正0也好,负0也好
是加上模,然后那个模去除以后又去掉了,剩下来的余数还是n个0
所以正0和负0的补码是一样的
那么刚才我们讲的是机器数有n位,这个n 如果在32位机器里面,这个n就是32
那么int型的数据占32位,short型的是16位,chart型呢是 8位。
下面我们来看一下变形补码的表示 那么前面我们已经讲过了补码的定义
那么在这个定义当中我们说求一个真值它的
这个补码表示,只要用这个模加上这个真值就可以了
当这个真值是一个正数的时候很显然
最终的这个补码当中的符号位肯定是0,而数值部分
不变,因为这样一个正数加上这个模,再取上那个模,剩下来的还是这个正数
那么当这个x是一个负数的时候,实际上这个地方
加一个负数相当于减一个 正数,减一个正数,减下来的这个符号位
一定是个1,也就是表示一个负数 然后数值部分也要进行变化,这个变化
就是各位取反,末位加1,就是原来这个X 它的真值,真正的值的数值部分各位取反,末位加1
得到这个负数的补码。
那么刚才 这个定义是一个2补码表示,也就是说我们的这个模是2的n次方
如果这个再加一位,也就是2的n+1次方
就是如果我们取的这个补码不是取n位的补码,而是取
n+1位的补码 那么这个里面有两个符号位,原来的一位符号位前面再加一位符号位
数值部分还是n-1位,那么这样的这个补码我们称为变形补码 也称为4's
comlement也就是 4,为什么是4?是因为双符号位,两位
符号位,2的2次方是4,所以它叫 变形补码。
那么比如说我们刚才 举的那个例子,0到8
这样的十进制数它对应的这个补码 如果是2补码的话,那么就是
符号位是0,数值部分和真值的数值部分一样
然后是8的时候,用原来的2补码表示在这儿
它的结果应该是1000,但是我们从这个形式上可以看到
如果最高位是1的话,说明它是一个负数
而真值是一个正数,正8,说明这个地方发生了溢出,有问题
但是如果我们用双符号位来表示的话 那么这个结果就可以不溢出
前面的这个0是它真正的符号位,是正数,然后这个1
在符号位上的1实际上是数值部分溢出到这个符号位上的这个1
那么这个1000相当于是8 这样就可以表示正8,如果多一位符号位用
变形补码表示,多一位符号位,这个结果就不溢出
那么如果是负数的话,各位取反,末位加1
就得到-0的补码,就是各位取反,就全1,再加1,就是
全0,变形补码也是全0,-1 的补码,各位取反,末位加1,就等于全1
-2是等于 负的010,-010就等于
符号位是负数,010各位取反就是101
然后末位再加1,就得到2补码,2的补码
或者是双符号位的这个变形补码 对应的这个等式。
-8那么就是 -1000
-1000,刚才我们已经举过例子了
就是1000各位取反就是0111
然后再末位加1,就是1000 用变形补码的话就是11000,这个用公式代进去就能够
这样子正确的结果,然后用各位取反,末位加1也能够得到相应的 正确的值。
所以在这儿我们可以看出用2补码表示的时候
在一个最大的一个正数 用2补码表示是无法表示的,它是溢出的
如果是用变形补码,4补码表示 它的最高位可以表示符号,然后
次高位的这个符号位可以用来表示一位有效数字
就是溢出的这个数值部分可以放到符号位上面,这样就可以表示正确的结果
所以通常我们在机器里面用这种变形补码
来存放中间结果,那么这些中间结果如果发生溢出也没有关系
我们可以用这个变形补码来表示,只要最终的结果不溢出就可以了
这是变形补码的这个应用 在这个里面我们可以看到这里+0和-0表示是唯一的
这个是+0、 -0的表示,最终都是全0
+0也是全0,-0也是全0,跟源码不一样
好,我们可以举一些例子来算一算这个真值的补码
假定我们的机器数有8位,也就是我们的模是等于2的8次方 如果我们有两个真值,一个是123,一个是-123
那么这两个数在机器里面它的这个补码表示应该是什么? 首先我们要把123的二进制表示要算出来
那么123的二进制表示我们可以用127-4=123来表示
而127我们马上就应该联想到它是
7个1,就是2的7次方减1
2的7次方等于128,128减1,那就是127
就是2的7次方是等于128
也就是等于100,后面有7个1
那么这个 减掉1,就是128减1等于127
等于11,这个是0,所以这边有7个1
就写这边7个1,这是127
减100,就相当于我们只要在这一位上减掉一个1,就是这一位上减掉一个1
所以我们很快能够得到最后的结果 就是011110
11,或者是0111011,只要把这个1 改成0,其他的照抄就可以了。
这样我们就很快能够得到123对应的二进制 数,所以我们不用短除法来进行运算。
只要用这种方式算就可以了。
有了123的二进制 表示,那么负123,那么就是负的0111011。
然后我们来看123的这个补码表示,也就是这个
01序列的补码表示,这个补码我们用公式来看的话就是
加上模,加上模以后就是1后面8个0,2的8次方。
这个很显然,加上去以后,得到的是1, 101111011。
再除上2的8次方,那么第一位的1,就是实际上这个1
就取模取掉了,剩下来的余数就是它本身,最后我们可以看到,正数的补码
就是对应的这个数本身。
那么我们通常用十六进制的来写二进制数。
那如果是负数的话,负的啊,这个123
我们用公式来带进去的时候,就是用 模加上这个数本身,这个数本身是个负数
所以我们用模减掉相应的这个绝对值。
那么在这我们可以把这个模写成 2的8次方写成8个1再加1。
就是相当于是,这边 加1,那么这个加1,加出来的
应该是0000001,也就是这个 2的8次方,2的8次方可以写成
8个1加1,这两个拆开来, 然后减去这个,照抄,嗯,这部分照抄。
然后我们把这个1写在后面,那么 1111减掉一个数,实际上是对这个数个位取反
因为1减1是等于0,1减0是等于1。
所以,原来这一位是1的话,用1 去减 它的结果就是0,原来这一位是0,用1去减去这个0
那么这一位就变成1,因此前面的这部分 相当于对后面这个数个位取反
然后加1,照抄,因此我们求一个数的
负数的补码,可以拿这个数,个位取反,末尾加1得到
个位取反,末尾加1,算出来的结果就是这个数。
这个数,等于85H,我们通常用十六进制来表示 [无声]
那么这个是个位取反,末尾加1,那么其实这个个位取反,末尾加1
它还可以用更简便的方法,来一下子就可以写出它的补码表示。
这个简便方法就是从右边往左边看,遇到的第一个1
前面的个位取反,就是 它的补码表示,所以在这个负数
求补当中,我们只要把这个1照抄,最后一个1照抄,
然后前面的这个1变成0,0变成1,1变成0,
1变成0,0变成1,最后的,就是它的补码表示, 也就是85H。
所以我们对于一个负数求补码,我们只要拿这个
对应的正数各位取反,末位加1就行,各位取反,末位加1
就相当于只要从后往前看,从最右边往左边看
碰到的第一个1一直不变,一直照抄,而第一个1前面的
各位取反就行,这是求真值的补码的一个简便方法。
那么这个是假定机器数是8位,如果机器数是16位呢?
那么结果也是一样的,只要这个地方改成2的16次方,
改成2的16次方,这前面如果有16位的话,前面 再添8跟1,这边前面再添
8跟1就可以,那么补码的真值
实际上我们前面讲的是求真值的补码,就是给一个123或负123这样的真值求它的
补码表示,就是01序列,如果我们 给出来的是一个补码,比如是一个01序列,怎样求这个
01序列对应的真正的值呢?它实际上是有一个公式的,那么这个公式
直接带进去算的时候,我们可以看出,比如说我们已经知道一个数
它的补码是这样的一个01序列,然后我们要算这个 01序列对应的真正的值,只要带到这个公式上去就可以了。
那么这边这个实际上就是n是等于8,一共有8位,
所以这边是2的7次方,这边是最高位的1, 那么1乘上2的7次方,就是1前面有一个负号,
然后带进去算,算出来的结果是负42。
然后是如果另外一个这个补码,它的真值要带进去算也是一样的, 最高位是0,所以是0乘上2的7次方。
前面加个负数,然后再加上2的6次方,2的4次方,2的2次方,2的1次方。
那么加起来是等于86,所以这个01序列对应的真值应该是86。
那么这是用公式来算的,理论上的求法,实际上呢我们直接用简便方法来算就行了。
那么这个简便方法是这样的,就符号位为0的时候,说明这个真值是一个正数,
数值部分是完全相同的,符号位为1,说明是个负数,我们只要把数值部分各位取反,末位加- 1就行。
比如说这个数它的真值 你一看最高位是0,表示它是一个正数,我们把0
转换成正,然后后面的数值部分照抄,完全相同。
这样的话我们把数值部分完全展开,那么就是这是
2的6次方加上2的4次方加上2的 2次方加上2的1次方。
也就说这个是一个负数,你看最高位是1,就是一个负数。
我们把1转换成负号,然后把后面的各位 取反,末位加1,也就是从最右边往左边看,
看到的第一个1, 整个照抄,第一个1前面的各位取反,1变成
0,0变成1,1变成0,0变成1,1变成0,
这样得到数值部分,那么数值部分
我们刚才讲了,这个个位取反,末尾加1的简便方法,就是从后面往前看 找到的第一个1前面的个位取反,嗯,我们刚才是这样算的。
这样子以后,我们得到的最终的真值是负的, 2的5次方加上2的3次方加上2的1次方,
也就是负40,这个是由编码
由这个补码表示的这个编码,来求真值的一个计算过程。
[音乐]
[音乐]