你找到的代码尝试解释非常原始的计算机硬件如何执行“加法”指令。我说“尝试”是因为我可以保证没有任何CPU使用这种方法,我会解释原因。
在日常生活中,您使用十进制数字并学习如何将它们相加:要添加两个数字,请添加最低两位数字。如果结果小于10,则写下结果并继续下一位数字位置。如果结果大于等于10,则写下结果减去10,继续下一个数字位置,但记得再加1。例如:23 + 37,您添加3 + 7 = 10,您写下0并记得为下一个位置添加1。在10s位置上,您添加(2 + 3)+ 1 = 6并写下。结果是60。
您可以对二进制数字执行完全相同的操作。区别在于,只有0和1是数字,因此可能的总和只有0、1、2。对于32位数字,您将逐个处理一个数字位置。这就是非常原始的计算机硬件所做的事情。
这段代码的工作方式不同。您知道两个二进制数字的和为2,如果两个数字都是1。因此,如果两个数字都是1,则会在下一个二进制位置添加1并写下0。那就是t的计算方式:它找到所有二进制位都为1的位置(即&),并将它们移动到下一个数字位置(即<< 1)。然后进行加法:0 + 0 = 0,0 + 1 = 1,1 + 0 = 1,1 + 1是2,但我们写下0。这就是异或运算符的作用。
但是,下一个数字位置中必须处理所有需要处理的1。这就是代码执行循环的原因:在下一次迭代中,将添加所有额外的1。
为什么没有处理器以这种方式执行?因为它是一个循环,处理器不喜欢循环,而且速度很慢。它很慢,因为在最坏的情况下,需要32次迭代:如果将1添加到数字0xffffffff(32个1位),则第一次迭代会清除y的位0并将x设置为2。第二次迭代会清除y的位1并将x设置为4。依此类推。需要32次迭代才能得到结果。但是,每次迭代都必须处理x和y的所有位,这需要大量的硬件。
一种原始的处理器会像你进行十进制算术运算一样快,从最低位到最高位依次进行。它也需要32个步骤,但每个步骤仅处理两个比特和前一个比特位置的一个值,因此更容易实现。即使在原始计算机中,人们也可以承受这样做而无需实现循环。
现代、快速和复杂的CPU将使用“条件求和加法器”。特别是如果比特数很高,例如64位加法器,它节省了大量时间。
一个64位的加法器由两部分组成:首先,一个32位的加法器用于最低的32位。那个32位的加法器产生一个总和和一个“进位”(指示必须添加1到下一个比特位置)。其次,为高32位提供两个32位的加法器:一个加x+y,另一个加x+y+1。所有三个加法器都是并行工作的。然后当第一个加法器产生它的进位时,CPU只需选择哪一个结果x+y或x+y+1是正确的,这样你就得到了完整的结果。因此,一个64位加法器只比一个32位加法器慢一点点,而不是两倍长。
32位加法器部件再次作为条件求和加法器实现,使用多个16位加法器,而16位加法器则是条件求和加法器,以此类推。
add
机器指令,这个指令几乎所有的CPU都有,并且作为硬件加法器实现,在几个时钟周期内完成运算。 - MikeCAT