【问题标题】:How to detect in LMC that calculation is greater than 999 and then output 999?如何在LMC中检测计算大于999然后输出999?
【发布时间】:2021-11-03 01:41:46
【问题描述】:

我需要编写一个LMC程序来解决a+bx+x2。进一步,如果结果大于999,则需要输出999;如果小于 999,则输出结果。

我已经完成了a+bx+x2部分,但是不知道溢出时如何输出999。

这是我的代码:

          IN
          STO a
          IN
          STO b
          IN 
          STO x
          LDA x
          STO x2
bx        LDA x
          BRZ end
          SUB one
          STO x
          LDA ans
          ADD b
          STO ans
          BR   bx
end       LDA ans
          LDA x2
          STO y
xx        LDA y
          BRZ END
          SUB ONE
          STO y
          LDA ANS
          ADD x2
          STO ANS
          BR   xx
END       LDA ANS
          ADD a
          STO ANS
          LDA ANS
          ADD ans
          SUB z
          BRP postive
          LDA ANS
          OUT
          HLT
postive   LDA z
          OUT
          HLT
a         DAT 000
b         DAT 000
x         DAT 000
x2        DAT 000
y         DAT 000
z         DAT 999
one       DAT 001
ONE       DAT 001
ans       DAT 000
ANS       DAT 000

【问题讨论】:

  • 您能对下面的答案提供一些反馈吗?
  • 您好,您有时间看答案吗?还是您不再感兴趣?

标签: computer-science little-man-computer


【解决方案1】:

您在计算上做得很好,确实很难检测到溢出(超过 999),因为通常 LMC 累加器无法存储更大的值,并且当发生这种溢出时,累加器的值未定义(在规范中),也没有指定是否设置“否定”标志。所以我们真的没有什么可以用来检测这种在所有 LMC 模拟器上兼容的溢出。

诀窍是将表达式计算为 999 - (? - ?? - ?²) 并检测 负溢出(低于 0),为此我们有 BRP 指令。如果没有负溢出,我们可以再次反转该结果,因为 999 - (999 - (? - ?? - ?²)) 与 ? - ?? - ?² 相同。这意味着您将 999 加载到 ans 中,然后您将使用 SUB 而不是 ADD,并且在每个 SUB 之后,您将检查是否存在负溢出,如果是,则转到将输出的块999.

其他说明

  • 请勿使用除大写外相同的标签。并非所有 LMC 模拟器都区分大小写。
  • 您不需要两个 ONE 也不需要两个 ANS 数据字段。
  • 最好在代码开头显式初始化ans,而不是依赖ans DAT 0这一事实。这是因为 LMC 具有 reset 功能,它不会 重置数据,而只会将程序计数器设置回顶部。这会导致错误的结果。
  • 您的乘法逻辑是正确的,但是您可以重复使用相同的代码来计算 ?? 和 ?²:意识到这个表达式等价于 (? + ?)?,因此您可以将 ? 和? 循环的每次迭代中的结果,因此执行一次乘法!

这里是更正和简化的代码:

#input:1 2 3
         INP
         STA a
         INP
         STA b
         INP
         STA x
         STA x2
         LDA z # "inverse" ans
         SUB a # do this first
loop     STA ans
         LDA x
         BRZ output
         SUB one
         STA x
         LDA ans
         SUB x2  # subtract both x...
         BRP continue
         BRA overflow
continue SUB b   # ... and b
         BRP loop

overflow LDA zero  # prepare for outputing 999 (overflow)
         STA ans
output   LDA z
         SUB ans # 999 - (999 - (a + bx + x^2))
         OUT
         HLT

a        DAT 0
b        DAT 0
x        DAT 0
x2       DAT 0
z        DAT 999
ans      DAT 0

zero     DAT 0
one      DAT 1




<script src="https://cdn.jsdelivr.net/gh/trincot/lmc@v0.816/lmc.js"></script>

你可以运行这个sn-p中的代码。默认输入已设置为 1 2 3,但您可以交互更改输入。

【讨论】:

  • 一个小问题,这里的下溢是正确的词吗?我认为这仍然是溢出,即使它是在负面的方向。
  • 是的,这是一个定义问题。我只是想与大于 999 的溢出区分开来。
  • 公平,那么“负溢出”在这里有用吗?
  • 这确实很有帮助。更新。谢谢!
猜你喜欢
  • 1970-01-01
  • 2013-10-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-12-30
  • 1970-01-01
  • 2016-07-12
  • 2022-09-26
相关资源
最近更新 更多