MIPS汇编编写递归函数输出结果错误问题排查求助
问题成因
你遇到的错误由两个核心问题导致:
- 执行流逻辑错误:x>0的分支完成计算后,没有跳转跳过基准情况的赋值代码,会直接执行
return_5段的li $v0,5,将返回值强制覆盖为5。这就导致所有递归调用拿到的子调用返回值永远是5,最终计算结果恒为2*5 +x = x+10,完全符合你给出的x=5输出15、x=6输出16的错误现象。 - 返回值寄存器不统一:你递归调用时默认从
$v0读取子调用的返回值,但x>0的计算结果被存在了$v1中,没有同步到$v0,同时主函数也错误地从$v1读取最终结果,寄存器使用逻辑混乱。
修复方案
你只需要调整两个位置的逻辑即可:
- 统一使用
$v0作为返回值寄存器,删除不必要的$v1使用 - x>0分支计算完成后,主动跳转到栈恢复逻辑(
terminate),跳过基准情况的赋值代码
修复后完整代码
.data prompt_string: .asciiz "Enter the number: " result: .asciiz "The result is: " .text .globl main main: li $v0,4 la $a0, prompt_string syscall # 读取输入数字 li $v0,5 syscall move $a0,$v0 jal function move $s7, $v0 # 现在统一从$v0取返回值 li $v0,4 la $a0, result syscall move $a0,$s7 li $v0,1 syscall li $v0,10 syscall function: # 栈帧保存 addi $sp, $sp, -12 sw $ra, 0($sp) sw $s0, 4($sp) sw $s1, 8($sp) add $s0,$zero, $a0 beq $s0,$zero, return_5 addi $a0,$s0,-1 jal function sll $v0,$v0,1 add $v0, $s0,$v0 # 结果直接存到$v0,统一返回寄存器 j terminate # 计算完成直接跳栈恢复,跳过基准赋值 return_5: li $v0,5 # 基准情况直接给$v0赋值 terminate: # 栈帧恢复 lw $ra, 0($sp) lw $s0, 4($sp) lw $s1, 8($sp) addi $sp,$sp,12 jr $ra
内容的提问来源于stack exchange,提问作者user16438868
相关产品推荐
相关产品推荐

