You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MIPS汇编需求:以半字读取存储无符号短整型输入

MIPS汇编作业:半字变量输入与存储实现方案

作业需求与当前问题

作业要求实现以下功能:

  • 定义三个short(半字)类型变量a、b、c
  • 提示用户输入三个无符号半字整数(范围0~65535)
  • 计算两个公式:
    • f = 15 * c / b + a % b
    • t = 10 * f / (a - b)
  • 以可读格式输出输入值与计算结果

当前已完成程序框架,但未实现半字形式的输入读取与存储,以下是原代码:

## data section
.data 
# 'a'lf I/O
a_input_ingerer: .asciiz "please enter a :"
a_output_ingerer: .asciiz "a= "

# 'b' I/O
b_input_ingerer: .asciiz "please enter b :"
b_output_ingerer: .asciiz " ,b= "

# 'c' I/O
c_input_ingerer: .asciiz "please enter c :"
c_output_ingerer: .asciiz " ,c="

# outputs
f_output_ingerer: .asciiz ",f= "
t_output_ingerer: .asciiz "t="

#equations
f_equation: .asciiz "\n f = 15 * c / b + a % b\n "
t_equation: .asciiz "\n t = 10 * f / (a - b)\n"


newline:.asciiz "\n"
newline_hastags: .asciiz "\n################\n "
newline_tab: .asciiz "\n \t"
newline_hastag: .asciiz "\n#"

## error massage
error:.asciiz "your number out of range"

###############
#code section
.text
.globl main

main:
##############################
## 'a'
##print the String

    la   $a0,a_input_ingerer
    li   $v0,4
    syscall 

##get the input
    la  $v0,5
    syscall  

## store the input in register $t1

    move $t1,$v0

#########
## 'b'
##print the String

    la   $a0,b_input_ingerer
    li   $v0,4
    syscall 

##get the input
    li $v0,5
    syscall  

## store the input in register $t2
    move $t2,$v0

#########
## 'a'
##print the String

    la   $a0,c_input_ingerer
    li   $v0,4
    syscall 

##get the input
    li $v0,5
    syscall  

## store the input in register $t3
    move $t3,$v0

#########

#calcolation
# f=(15*c/b)+(a%b)
#(15*c/b) save it at $t4
    sll $t4,$t3,0
    sll $t5,$t3,1
    sll $t6,$t3,2
    sll $t7,$t3,3

    add $t4,$t5,$t4
    add $t4,$t6,$t4
    add $t4,$t7,$t4

    div $t4,$t2
    mflo $t4
#(a%b)
    div $t1,$t2
    mfhi $t5

# (15*c/b)+(a%b)
# $t4  + $t5 save it $t4
    add $t4,$t5,$t4

######
# t=10*f/(a-b
# 10*f and save it in $t5
    sll $t5,$t4,1
    sll $t6,$t4,3
    add $t5,$t5,$t6

#(a-b)and save it in $t6
    sub $t6,$t1,$t2

# 10*f / (a-b) and save it in $t5
# $t5 / $t6
    div $t5,$t6
    mflo $t5

########################## 
#Output
#first equation input
    la $a0, a_output_ingerer
    li $v0,4
    syscall

    move $a0,$t1

    li $v0,1
    syscall


    la $a0,b_output_ingerer
    li $v0,4
    syscall 

    move $a0,$t2

    li $v0,1
    syscall

    la $a0,c_output_ingerer
    li $v0,4
    syscall

    move $a0,$t3

    li $v0,1
    syscall

##first equation

    la $a0,f_equation
    li $v0,4
    syscall

#first equation result

    la $a0,f_output_ingerer
    li $v0,4
    syscall 

    move $a0,$t4
  
    li $v0,1
    syscall

###############################
    la $a0,newline_hastags
    li $v0,4
    syscall 

#second equation input

    la $a0, a_output_ingerer
    li $v0,4
    syscall

    move $a0,$t1

    li $v0,1
    syscall

    la $a0,b_output_ingerer
    li $v0,4
    syscall 

    move $a0,$t2

    li $v0,1
    syscall

    la $a0,f_output_ingerer
    li $v0,4
    syscall

    move $a0,$t4

    li $v0,1
    syscall


##second equation
    la $a0,t_equation
    li $v0,4
    syscall

#second equation result 
    la $a0,t_output_ingerer
    li $v0,4
    syscall 
  
    move $a0,$t5

    li $v0,1
    syscall

#######################################

#system call for termainating the exeuction

    li $v0,10
    syscall 

修改方案与完整代码

修改要点

  1. 定义半字变量:在.data段添加半字类型的存储单元
  2. 输入校验与存储:读取整数后校验范围,符合要求用sh指令存入半字变量
  3. 无符号半字加载:用lhu指令加载变量,保留无符号属性
  4. 边界错误处理:添加除零检查,避免运行时崩溃

修改后的完整代码

## data section
.data 
# 半字变量定义
a: .half 0
b: .half 0
c: .half 0

# 'a' I/O
a_input_integer: .asciiz "please enter a :"
a_output_integer: .asciiz "a= "

# 'b' I/O
b_input_integer: .asciiz "please enter b :"
b_output_integer: .asciiz " ,b= "

# 'c' I/O
c_input_integer: .asciiz "please enter c :"
c_output_integer: .asciiz " ,c="

# outputs
f_output_integer: .asciiz ",f= "
t_output_integer: .asciiz "t="

# equations
f_equation: .asciiz "\n f = 15 * c / b + a % b\n "
t_equation: .asciiz "\n t = 10 * f / (a - b)\n"

newline:.asciiz "\n"
newline_hastags: .asciiz "\n################\n "

## error messages
error_range:.asciiz "Error: number out of unsigned half-word range (0~65535)\n"
error_div_zero:.asciiz "Error: division by zero\n"

###############
# code section
.text
.globl main

main:
##############################
## 读取并存储a
# 提示输入
la   $a0, a_input_integer
li   $v0, 4
syscall 

# 读取整数
li  $v0, 5
syscall  

# 校验范围:无符号半字最大为65535
li $t0, 65535
bgt $v0, $t0, out_of_range
blt $v0, $zero, out_of_range # 无符号数不能为负

# 存储到半字变量a
sh $v0, a

#########
## 读取并存储b
# 提示输入
la   $a0, b_input_integer
li   $v0, 4
syscall 

# 读取整数
li $v0, 5
syscall  

# 校验范围
bgt $v0, $t0, out_of_range
blt $v0, $zero, out_of_range
# 检查b是否为0
beq $v0, $zero, div_by_zero

# 存储到半字变量b
sh $v0, b

#########
## 读取并存储c
# 提示输入
la   $a0, c_input_integer
li   $v0, 4
syscall 

# 读取整数
li $v0, 5
syscall  

# 校验范围
bgt $v0, $t0, out_of_range
blt $v0, $zero, out_of_range

# 存储到半字变量c
sh $v0, c

#########
# 加载半字变量到寄存器(无符号加载lhu)
lhu $t1, a
lhu $t2, b
lhu $t3, c

# 计算f = 15*c/b + a%b
# 计算15*c:15=8+4+2+1,用移位加法实现
sll $t4, $t3, 3  # 8*c
sll $t5, $t3, 2  #4*c
sll $t6, $t3, 1  #2*c
add $t4, $t4, $t5 #8c+4c=12c
add $t4, $t4, $t6 #12c+2c=14c
add $t4, $t4, $t3 #14c+c=15c

# 15c / b,结果存$t4
div $t4, $t2
mflo $t4

# a%b,结果存$t5
div $t1, $t2
mfhi $t5

# f = 15c/b + a%b,结果存$t4
add $t4, $t4, $t5

######
# 计算t = 10*f/(a-b)
# 计算10*f:10=8+2
sll $t5, $t4, 3  #8*f
sll $t6, $t4, 1  #2*f
add $t5, $t5, $t6 #8f+2f=10f

# 计算a-b,存$t6
sub $t6, $t1, $t2
# 检查除数是否为0
beq $t6, $zero, div_by_zero

# 10f/(a-b),结果存$t5
div $t5, $t6
mflo $t5

########################## 
# 输出部分
# 输出输入值
la $a0, a_output_integer
li $v0,4
syscall

move $a0,$t1
li $v0,1
syscall

la $a0,b_output_integer
li $v0,4
syscall 

move $a0,$t2
li $v0,1
syscall

la $a0,c_output_integer
li $v0,4
syscall

move $a0,$t3
li $v0,1
syscall

# 输出f的公式与结果
la $a0,f_equation
li $v0,4
syscall

la $a0,f_output_integer
li $v0,4
syscall 

move $a0,$t4
li $v0,1
syscall

###############################
la $a0,newline_hastags
li $v0,4
syscall 

# 输出t的输入依赖与公式
la $a0, a_output_integer
li $v0,4
syscall

move $a0,$t1
li $v0,1
syscall

la $a0,b_output_integer
li $v0,4
syscall 

move $a0,$t2
li $v0,1
syscall

la $a0,f_output_integer
li $v0,4
syscall

move $a0,$t4
li $v0,1
syscall

la $a0,t_equation
li $v0,4
syscall

# 输出t的结果
la $a0,t_output_integer
li $v0,4
syscall 

move $a0,$t5
li $v0,1
syscall

# 正常退出
li $v0,10
syscall 

# 错误处理分支
out_of_range:
la $a0, error_range
li $v0,4
syscall
li $v0,10
syscall

div_by_zero:
la $a0, error_div_zero
li $v0,4
syscall
li $v0,10
syscall 

修改细节说明

  • 半字变量定义:用.half指令分配2字节存储单元,符合short类型要求
  • 输入校验:确保输入值在0~65535范围内,不符合则输出错误并退出
  • 半字操作:用sh(存储半字)和lhu(无符号加载半字)指令,保证数据以半字形式存储且保留无符号属性
  • 除零检查:对b=0和a-b=0的情况做判断,避免运行时除法错误

内容的提问来源于stack exchange,提问作者محمد العر</think_never_used_51bce0c785ca2f68081bfa7d91973934>

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.25 07:06:34