添加两个数字以生成两位数字
问题描述:
我想将两个预定义值一起添加并生成结果。 我的代码现在正在做的是将16和6加在一起,这应该打印出22。然而,它打印出2 ...我真的不知道如何纠正这...添加两个数字以生成两位数字
这里是代码:
data segment ; data segment. Keyword db means define byte. You can also define word (dw)
numA db 16 ;Define first variable
numB db 06 ;Define second variable
StrMsg db 'The answer is $' ;return message to the user
leng db 1 ;length of the charachters - this value will be overwritten
data ends
; stack segment
stack1 segment stack
db 100 dup(?) ; This is the stack of 100 bytes
stack1 ends
code segment
assume cs:code, ds:data, ss:stack1
start:
;Perform initialization
mov ax, data ;Put the starting address of the data segment into the ax register (must do this first)
mov ds, ax ;Put the starting address of the data segment into the ds register (where it belongs)
mov ax, stack1 ;Put the starting address of the stack into the ax register (must do this first)
mov ss, ax ;Put the starting address of the stack segment into the ss register (where it belongs)
mov al, numA ;move numA to ax
add al, numB ;ax contains numa + numb
mov dl, al ;move result to dl for display
lea dx, StrMsg ;load message to display the result to the user
mov ah, 9h ;display string subroutine
int 21h ;interrupt for MS-DOS routine
add dl, 30h ;Add 30h for ASCII table offset
mov ah, 2h ;Store interrupt code in ah to display results in dl
int 21h ;display character in dl as translated by ascii code
mov ah, 4ch ;Set up code to specify return to dos
int 21h ;Interpt number 21 (Return control to dos prompt)
code ends
end start
答
如果你真的只想要得到一个两位数的十进制数(如标题所暗示的),你可以使用AAM
:
data segment ; data segment. Keyword db means define byte. You can also define word (dw)
numA db 16 ;Define first variable
numB db 06 ;Define second variable
StrMsg db 'The answer is $' ;return message to the user
leng db 1 ;length of the charachters - this value will be overwritten
data ends
; stack segment
stack1 segment stack
db 100 dup(?) ; This is the stack of 100 bytes
stack1 ends
code segment
assume cs:code, ds:data, ss:stack1
start:
;Perform initialization
mov ax, data ;Put the starting address of the data segment into the ax register (must do this first)
mov ds, ax ;Put the starting address of the data segment into the ds register (where it belongs)
mov ax, stack1 ;Put the starting address of the stack into the ax register (must do this first)
mov ss, ax ;Put the starting address of the stack segment into the ss register (where it belongs)
lea dx, StrMsg ;load message to display the result to the user
mov ah, 9h ;display string subroutine
int 21h ;interrupt for MS-DOS routine
mov al, numA ;move numA to al
add al, numB ;al contains numa + numb
lea di, StrMsg ; Place for target string (The old value of StrMsg isn't used anymore)
aam ; AL => AH (first dec. digit) AL (second dec. digit) (unpacked BCD)
or ax, 3030h ; Convert both digits to ASCII
mov BYTE PTR [di], ah ; Store first digit
mov BYTE PTR [di+1], al ; Store second digit
mov BYTE PTR [di+2], '$' ; Store termination character for 'int 21h fn 09h'
lea dx, StrMsg ;load message to display the result to the user
mov ah, 9h ;display string subroutine
int 21h ;interrupt for MS-DOS routine
mov ah, 4ch ;Set up code to specify return to dos
int 21h ;Interpt number 21 (Return control to dos prompt)
code ends
end start
如果你也想得到一个三位十进制数字,你可以将数字隔开两个部分。首先除以100,结果得到第一位数字。然后除以10的余,你会得到的第二位,而第三位是余数:
data segment ; data segment. Keyword db means define byte. You can also define word (dw)
numA db 16 ;Define first variable
numB db 06 ;Define second variable
StrMsg db 'The answer is $' ;return message to the user
leng db 1 ;length of the charachters - this value will be overwritten
data ends
; stack segment
stack1 segment stack
db 100 dup(?) ; This is the stack of 100 bytes
stack1 ends
code segment
assume cs:code, ds:data, ss:stack1
start:
;Perform initialization
mov ax, data ;Put the starting address of the data segment into the ax register (must do this first)
mov ds, ax ;Put the starting address of the data segment into the ds register (where it belongs)
mov ax, stack1 ;Put the starting address of the stack into the ax register (must do this first)
mov ss, ax ;Put the starting address of the stack segment into the ss register (where it belongs)
lea dx, StrMsg ;load message to display the result to the user
mov ah, 9h ;display string subroutine
int 21h ;interrupt for MS-DOS routine
mov al, numA ;move numA to ax
add al, numB ;ax contains numa + numb
mov dl, al ;move result to dl for display
lea di, StrMsg ; Place for target string (The old value of StrMsg isn't used anymore)
call al2dec
lea dx, StrMsg ;load message to display the result to the user
mov ah, 9h ;display string subroutine
int 21h ;interrupt for MS-DOS routine
mov ah, 4ch ;Set up code to specify return to dos
int 21h ;Interpt number 21 (Return control to dos prompt)
al2dec PROC ; Args: AL register to convert, DS:DI pointer to target string
mov bl, 100
xor ah, ah ; Clear AH for division
div bl ; AL = AX/BL remainder AH
or al, 30h ; Convert result to ASCII
mov BYTE PTR [di], al ; Store as first digit
shr ax, 8 ; Shift remainder into AL, clear AH
mov bl, 10
div bl ; AL = AX/BL remainder AH
or al, 30h ; Convert result to ASCII
mov BYTE PTR [di+1], al ; Store as second digit
or ah, 30h ; Convert remainder to ASCII
mov BYTE PTR [di+2], ah ; Store as third digit
mov BYTE PTR [di+3], '$' ; Store at last termination character for 'int 21h fn 09h'
ret
al2dec ENDP ; DS:DI contains string with decimal digits
code ends
end start
如果你在前面的零干扰,可以通过反复划分隔离相反的顺序数字10.这也是最常用的方法,如果你想转换更大的数字:
al2dec PROC ; Args: AL register to convert, DS:DI pointer to target string
mov bl, 10 ; Base 10 -> divisor
xor cx, cx ; CX=0 (number of digits)
al2dec_loop_1: ; 1st loop
xor ah, ah ; Clear AH for division (don't forget it!)
div bl ; AL = AX/BL Remainder AH
push ax ; Push remainder for LIFO in Loop_2
add cl, 1 ; Equivalent to 'inc cl'
test al, al ; AL = 0?
jnz al2dec_loop_1 ; No: once more
al2dec_loop_2: ; 2nd loop
pop ax ; Get back pushed digits
or ah, 00110000b ; Conversion to ASCII
mov BYTE PTR [di], ah ; Store only AH to [DS:DI] (DI is a pointer to a string)
add di, 1
loop al2dec_loop_2 ; Until there are no digits left
mov BYTE PTR [di], '$' ; Store termination character for 'int 21h fn 09h'
ret ; Ret: DS:DI contains decimal '$'-terminated ASCII-String
al2dec ENDP
由于你只打印1个字符,你不应该感到惊讶。要处理双位数字,您可能需要打印十位和一位数字。根据小学数学,这将是除以10的商和余数。 – Jester 2014-10-31 16:11:09
请为您使用的汇编程序添加标签([tasm]或[masm]) – rkhb 2014-10-31 19:05:08