2012-04-07 3 views
1

부호없는 정수를 인수로 가져 와서 정수의 모든 십진수 합계를 재귀 적으로 반환하는 MIPS 프로그램을 작성하려고합니다. 예를 들어 인수가 75080이면 반환되는 합은 20 (7 + 5 + 0 + 8 + 0)입니다. 지금까지 제 코드가 있습니다. 어떤 도움을 주시면 감사하겠습니다.MIPS, 재귀

내 사고 방식은 숫자를 마지막 정수와 함께 남겨두고 숫자를 10으로 나눠서 mfhi를 사용하여 미리 알림을 추가하는 것이 었습니다.

.data 
prompt: .asciiz "Enter a string of integer: " 
output: .asciiz "\nThe total sum is: " 
    .text 
    .globl main 
main: 
    la $a0, prompt 
    li $v0, 4 
    syscall 

    li $v0, 5 
    syscall 

    move $t2, $v0 

    la $a0, output 
    li $v0, 4 
    syscall 

Loop: 
    div $t2, $t2, 10 
    mflo, $t1 
    mfhi, $t3 
    beqz $t1, Exit 
    add $t1, $t1, 0 
    b additive 

additive: 
    add $t0, $t1, $t1 
    j Loop 

Exit: 
     la $a0, output 
      li $v0, 4 
      syscall 
      la $v0, 10 
      syscall 
+0

syscall 4를 사용하면 버퍼 길이를 지정하지 않고 프롬프트를 인쇄 할 수 있으며 syscall 5는 이미 정수로 변환 된 입력을 가져옵니다. – Kaz

+0

MIPS가 이런 식인지 아닌지는 기억이 나지 않지만 일부 시스템에서는 높은 명령에서 낮은 명령으로 이동하는 명령이 중요합니다. MIPS에 대해 기억하는 것이 맞다면 실제로 유효 할 것입니다. 이 거꾸로. –

+0

이것은 http://stackoverflow.com/questions/10031785/iteration-and-recursive-in-mips의 재 게시입니다. – bta

답변

0
  • 는이 일을 할 무슨 뜻이야? $t1$t3,이 $t1에있는 지수로 나누어 복사 한 후

    add $t1, $t1, 0

  • 나머지$t3에 있습니다 레지스터에 0을 추가하면 그 값을 변경하지 않습니다. 당신이 총계에 더할 때 당신은 그것을 다른 방향으로 대하는 것입니다.

  • 이것은 실제로 당신에게 $t0 = 2 * $t1을 줄 것입니다 : $t1을 추가하고 그 결과를 $t0에 저장하고 있습니다.

    add $t0, $t1, $t1

    당신은 아마 실제로 원하는 : 가장 중요한 숫자가 추가되지 얻을 않을 것이다, 그래서 당신은 총에 나머지를 추가 $t1 == 0이전 확인하고

    add $t0, $t0, $t3

  • . 전체에 더하기 위해 서브 루틴이 필요하지 않습니다. beqz Exit ->b Loop 대신 bnez Loop을 사용할 수도 있습니다. 마지막으로 몫이 $t2이므로 이미 $t1이 필요하지 않습니다.

이 함께 Loopadditive 제거하고 교체하기 :

Loop: 
    div $t2, $t2, 10 
    mfhi, $t3 
    add $t0, $t0, $t3 
    bnez $t2, Loop 
  • 귀하의 Exit는 이상한 : 당신이 output 캐릭터를 두 번째로 인쇄 대신 정수를 인쇄하고 있습니다. 이것에

변경이 :

Exit: 
    move $a0, $t0 
    la $v0, 1 
    syscall 

    la $v0, 10 
    syscall 
0

접근 방식은 매우 간단합니다. 당신은 재귀 함수가 필요합니다, 나는 마지막 자릿수를 취할 인수 Sum의 모든 자릿수에 대한 절차를 반복합니다. 재귀 호출이 반환되면 이전 결과에 숫자가 추가됩니다. 이 코드는 이해하기 쉽도록 주석 처리되어 있습니다. 코드는 다음과 같습니다 :

.text 

#calculates sum of digits recursively 
SumDigits: 

    sub  $sp, $sp, 12     #alloocate 12B on stack 
    sw  $ra 0($sp)      #save return address 
    sw  $a0, 4($sp)      #save argument 

    beq  $a0, $0, exit_sumdigits  #when there is no more digits return 0 
    rem  $t0, $a0, 10     #get last digit 
    sw  $t0, 8($sp)      #save it on stack 
    div  $a0, $a0, 10     #divide argument by 10 
    jal  SumDigits      #repeat procedure 
    lw  $t0, 8($sp)      #read digit from stack 
    add  $v0, $v0, $t0    #add digit to previous result 
    lw  $ra, 0($sp)      #load return address 
    addi $sp, $sp, 12     #free stack 
    jr  $ra        #return 

exit_sumdigits: 
    li  $v0, 0       #there are no more digits, return 0 
    lw  $ra, 0($sp)      #load return address 
    addi $sp, $sp, 12     #free stack 
    jr  $ra        #return 

main: 
    li  $a0, 75080      #load number in $a0 
    jal  SumDigits       #call SumDigits 

    move $a0, $v0       #set a0 = result of SumDigits 
    li  $v0, 1       #set $v0 for print int system call 
    syscall 

    li  $v0, 10       #set $v0 for exit system call 
    syscall 

.data