用匯編語言實現(xiàn)兩個數(shù)相加,并考慮進位情況(兩個數(shù)都是用一個字節(jié)儲存的)
1. 首先貼代碼
assume cs:code,ds:data
data segment
op1 DB 09h
op2 DB 08h
defult db ?
carry db ?
data ends
code segment
start:
mov ax,data
mov ds,ax
mov al,op1
add al,op2
AAA
jc ss2
jnc ss1
ss1:mov carry,30H
ss2:mov carry,31h
ss3:mov defult,al
add defult,30h
mov dl,carry
mov ah,2
int 21h
mov dl,defult
mov ah,2
int 21h
mov ah,4ch
int 21h
code ends
end start
2 .方法
首先將操作數(shù)(operand)op1與op2的和存到寄存器al中,
然后利用AAA命令將al中的值調(diào)整到非壓縮的BCD格式.
之后用jc和jnc命令判斷是否有進位,
如果有,將carry賦值為31h,否則將carry賦值為30h,
并將al中的值賦給defult,之后把defult轉(zhuǎn)換成字符的形式,
最后分別打印出carry(表示結(jié)果的高八位)和defult(結(jié)果的低八位)即可.
3. 解釋
(1) AAA指令:將al中的值調(diào)整到非壓縮的BCD格式
比如執(zhí)行 ADD AL,BL 之后,AL的值是15,AAA調(diào)整后變成用AH、AL表示非壓縮BCD碼的15,即AH=1,AL=5,不影響其它通用寄存器的值。
(2) jc、jnc和jmp指令
jc:當cf=1(即進位標志位為1,也就是說進位了)時,則轉(zhuǎn)移.
上文代碼中命令 jc ss2 ,意思就是轉(zhuǎn)移到了ss2.之后執(zhí)行ss2和其之后的語句,而不會返回到跳轉(zhuǎn)語句并執(zhí)行其后的語句.
jnc:當cf=0(即進位標志位為0,也就是沒有進位)時,則轉(zhuǎn)移.
上文代碼中命令 jnc ss1 ,意思就是轉(zhuǎn)移到了ss1.之后執(zhí)行ss2和其之后的語句,而不會返回到跳轉(zhuǎn)語句并執(zhí)行其后的語句.
這兩個代碼用于對 是否進位 的判斷.
jmp:表示無條件的轉(zhuǎn)移.如同上文兩個跳轉(zhuǎn)命令一樣,也不會返回.
(3) 為什么把31h/30h賦給carry
查找ASCII['?ski]表,可以知道30h/31h表示序號48/49,分別對應(yīng)著ASCII表中的十進制數(shù)0/1,也就是說如果進位,則把carry賦值為1,如果不進位,把carry賦值為0.其中carry表示為結(jié)果的高八位.
(4) 如何將defult中的值轉(zhuǎn)變成字符類型的十進制數(shù)?
執(zhí)行指令 add defult,30h.
因為30h是ASCII表中十進制數(shù) 0 的序號,所以defult中的值加上30h之后就可以轉(zhuǎn)變成字符類型的十進制數(shù).
參考資料:
加法的非壓縮BCD碼調(diào)整指令A(yù)AA:
https://bbs.csdn.net/topics/290073229
匯編 簡單的兩個一位數(shù)相加
https://blog.csdn.net/iaiti/article/details/9348421