-2

我和我的朋友正在尝试编写一个代码,我们需要将两个 32 位数字相乘得到一个 64 位数字。我们想使用 add 方法将数字相乘,问题是寄存器一次只能存储 8 位(一对 16 位)。我们一直在寻找解决方案,但很难找到对这种情况真正有帮助的东西。你能给我们一些关于如何做到这一点的提示吗?

4

2 回答 2

2

加法是加法,我们在小学学过加法。

 99
+ 1
====

9+1 = 0 进位,我们这样做两次,然后得到 0+1 = 1

 11
  99
+  1
====
 100

不管是什么基础,在二进制中我们可以有这个:

 111
+001
====

同样的交易,以 2 为底,1+1 = 0 携带 1,重复此操作直到 1+0 = 1

 111
  111
+ 001
=====
 1000

但与纸和铅笔不同的是,我们对计算机的位数有更严格的限制,但这丝毫不会改变它的工作方式。

我可以把前面的问题分成两个位大小的寄存器。

 11 11
  1  11
+ 0  01
===  ==
 10  00

第一个是低位两位 11+01 我们进行数学运算并得到 00,进位为 1。第二个操作将前一个操作的进位用作进位,然后我们添加 01 + 00进位为 1,进位为 0 得到 10。

那里没有什么魔法。

然后让我们变得更基础

 01 11 11 10
  0  1  1  1
+ 0  0  0  1
 == == == ==
  1  0  0  0 

我们从 lsbit 开始,它是 1+1,进位为 0,因此 0+1+1 = 0,进位为 1。该进位是下一列的进位,即二进制列。这是 1 的进位加 1 + 0 = 0 和 1 的进位。四列与二进位 1 + 1 + 0 = 0 和 1 的进位相同。八列是进位1 + 0 + 0 = 1,进位为 0。每一列的工作原理相同,将进位加操作数 a 加操作数 b 加在一起,然后得到一个结果位和一个进位位。您可以根据需要将它们链接在一起,数百万位,数十亿位,无限。

所以大会通常在这里给你一些支持。您的 alu 往往有一个进位,该进位往往会进入某些处理器状态寄存器中的进位标志位。你有你的两个操作数,结果,中间进位变成进位是在 alu 本身中管理的,你看不到那些。有时你有一个普通的加法指令和另一个带进位指令的加法指令,其中进位标志是进位,然后进位也落在那个进位位,所以对于这样的系统,你会

add
adc
adc
adc
...

对于您想要的一组值,通常受您拥有的内存量或其他类似限制(寄存器数量)的限制。

如果你没有带进位的加法,那么你必须合成它

add
jnc lab0
add #1
lab0:
add
jnc lab1
add #1
lab1:

一些指令集只有一个带进位的加法,所以

clc ; clear carry bit
add
add
add
add
...

我显然将寄存器/操作数从这些指令中剔除,因为它们对于“我如何做大于寄存器中位数的数学运算”类型的问题并不重要。如上所示的 1 位和 2 位数学,您需要准备数据并将其放置在基于您正在处理的列的操作数中。如果您有 8 位寄存器和 8 位 alu,那么您将 N 位操作数划分为 8 位部分,组织它们以便您首先处理低字节,然后在第二个添加中处理下一个高阶字节,依此类推。正确地将您从一个阶段的进位链接到下一个阶段的进位。

不知道为什么在寻找解决方案时有任何问题。小学数学涵盖了计数和加法的基础知识,并延续到下一列,然后您将其带到指令集文档中,其中描述了加法以及是否有进位加法。可见加法操作修改进位位,加进位加法使用和修改进位位。

于 2013-12-20T21:07:14.967 回答
0

让这两个数字是 AA55h 和 BB22h。我们将使用第二个数字作为计数器。碱性磷酸酶是:

LXI B、AA55h LXI D、BB22h;计数器 LXI H,0000h;16位进位初始化

开始: MOV A,C ADD C MOV C,A

MOV A,B ADC B MOV B,A

JNC 进位 INX H 进位:DCX D;递减计数器 JNZ Start

;;16 位进位已存入 HL 对 ;;16 位结果已存入 BC 对

于 2014-12-05T09:30:32.173 回答