@_@汇编T_T

目录

题目描述

AC代码

思路分析


题目描述

Nim是一个简单的双人游戏,可能起源于中国。游戏中使用的计数器类型有很多种类,如石头、火柴、苹果等。游戏界面被划分为很多行,每行中有数量不等的计数器:

行号

计数器数量

1

○○○

2

○○○○○○

……

……

n

○○○○○○○○○○

本次实验对Nim游戏做了一些小的改变,具体如下:游戏界面由三行组成,计数器类型为石头,其中A行包含3个石头,B行包含5个石头,C行包含8个石头。

规则如下:

⑴ 每个玩家轮流从某一行中移除一个或多个石头。

⑵ 一个玩家不能在一个回合中从多个行中移除石头。

⑶ 当某个玩家从游戏界面上移除最后剩余的石头时,此时游戏结束,该玩家获胜。

要求

⑴ 在游戏开始时,你应该显示游戏界面的初始化状态。具体包括:在每行石头的前面,你应该先输出行的名称,例如“ROW A”。你应该使用ASCII字符小写字母“o”(ASCII码 x006F)来表示石头。游戏界面的初始化状态应该如下:

ROW A: ooo

ROW B: ooooo

ROW C: oooooooo

⑵ 游戏总是从玩家1先开始,之后玩家1和玩家2轮流进行。在每一个回合开始时,你应该输出轮到哪一个玩家开始,并提示玩家进行操作。例如,对于玩家1,应该有如下显示:

Player 1,choose a row and number of rocks:

⑶ 为了指定要移除哪一行中的多少石头,玩家应该输入一个字母后跟一个数字(输入结束后不需要按Enter键),其中字母(A,B或C)指定行,数字(从1到所选行中石头的数量)指定要移除的石头的数量。你的程序必须要确保玩家从有效的行中移除有效数量的石头,如果玩家输入无效,你应该输出错误提示信息并提示该玩家再次进行输入。例如,如果轮到玩家1:

Player 1, choose a row and number of rocks: D4

Invalid move. Try again.

Player 1, choose a row and number of rocks: A9

Invalid move. Try again.

Player 1, choose a row and number of rocks: A*

Invalid move. Try again.

Player 1, choose a row and number of rocks: &4

Invalid move. Try again.

Player 1, choose a row and number of rocks:

你的程序应保持提示玩家,直到玩家选择有效的输入为止。确保你的程序能够回显玩家的输入到屏幕上,当回显玩家的输入后,此时应该输出一个换行符(ASCII码x000A)使光标指向下一行。

⑷ 玩家选择有效的输入后,你应该检查获胜者。如果有一个玩家获胜,你应该显示相应的输出来表明该玩家获胜。如果没有胜利者,你的程序应该更新游戏界面中每行石头的数量,重新显示更新的游戏界面,并轮到下一个玩家继续。

⑸ 当某个玩家从游戏界面上移除最后的石头时,游戏结束。此时,你的程序应该显示获胜者然后停止。例如,如果玩家2移除了最后的石头,你的程序应该输出一下内容:

Player 2 Wins.

样例输入/输出

ROW A: ooo
ROW B: ooooo
ROW C: oooooooo
Player 1, choose a row and number of rocks: B2
ROW A: ooo
ROW B: ooo
ROW C: oooooooo
Player 2, choose a row and number of rocks: A1
ROW A: oo
ROW B: ooo
ROW C: oooooooo
Player 1, choose a row and number of rocks: C6
ROW A: oo
ROW B: ooo
ROW C: oo
Player 2, choose a row and number of rocks: G1
Invalid move. Try again.
Player 2, choose a row and number of rocks: B3
ROW A: oo
ROW B:
ROW C: oo
Player 1, choose a row and number of rocks: A3
Invalid move. Try again.
Player 1, choose a row and number of rocks: C2
ROW A: oo
ROW B:
ROW C:
Player 2, choose a row and number of rocks: A1
ROW A: o
ROW B:
ROW C:
Player 1, choose a row and number of rocks: A*
Invalid move. Try again.
Player 1, choose a row and number of rocks: &4
Invalid move. Try again.
Player 1, choose a row and number of rocks: A1
Player 1 Wins.
----- Halting the processor -----

提示与建议

⑴ 记住,程序中所有的输入输出使用ASCII字符,你应该负责进行必要的转换。

⑵ 从键盘中输入字符你应该使用TRAP x20(GETC)指令,同时为了回显输入的字符到屏幕上,你应该使用TRAP x21(OUT)指令,该指令紧跟在TRAP x20指令之后。

⑶ 你应该在适当的时候使用子程序。

⑷ 在你编写的每个子程序中,应该保存并还原所使用的任何寄存器。这将避免你在调试过程中遇到问题。

⑸ 在一个回合中,玩家的输入必须包含指定为A,B或C(即大写字母)的行,后面紧跟不大于该行仍然存在的石头数量的数字。

提示:

① 你应该设置程序的开始地址在x3000(如,程序的第一行指令应该为 .ORIG x3000)

② 源文件命名为nim.asm

AC代码

 .orig x3000again    jsr printjsr datain1jsr printjsr datain2br againprint   st r0,save_r0st r1,save_r1st r7,save_r7lea r0,row_aputsld r0,stoneld r1,num_a
loop_a  outadd r1,r1,#-1brp loop_ald r0,croutlea r0,row_bputsld r0,stoneld r1,num_b
loop_b  outadd r1,r1,#-1brp loop_bld r0,croutlea r0,row_cputsld r0,stoneld r1,num_c
loop_c  outadd r1,r1,#-1brp loop_cld r0,croutld r0,save_r0ld r1,save_r1ld r7,save_r7retsave_r0 .fill #0
save_r1 .fill #0
stone   .fill x006f
cr  .fill x000d
row_a   .stringz "ROW A: "
row_b   .stringz "ROW B: "
row_c   .stringz "ROW C: "
num_a   .fill #3
num_b   .fill #5
num_c   .fill #8cue1    st r0,save_r0st r7,save_r7lea r0,play1putsld r0,save_r0ld r7,save_r7ret
play1   .stringz "Player 1,choose a row and number of rocks:"cue2 st r0,save_r0st r7,save_r7lea r0,play2putsld r0,save_r0ld r7,save_r7ret
play2   .stringz "Player 2,choose a row and number of rocks:"
save_r7 .fill #0datain1 st r0,save_r0st r2,save_r2st r3,save_r3st r7,saver7
try1    jsr cue1getcoutadd r2,r0,#0not r2,r2add r2,r2,#1getcoutadd r3,r0,#0ld r0,lfout
test1a  ld r0,char_aadd r0,r2,r0brnp test1bld r0,char_0not r0,r0add r0,r0,#1add r0,r0,r3brn error1ld r3,num_anot r0,r0add r0,r0,#1add r3,r0,r3brn error1st r3,num_ald r3,sum_abcadd r3,r3,r0brz win1st r3,sum_abcbr save
test1b  ld r0,char_badd r0,r2,r0brnp test1cld r0,char_0not r0,r0add r0,r0,#1add r0,r0,r3brn error1ld r3,num_bnot r0,r0add r0,r0,#1add r3,r0,r3brn error1st r3,num_bld r3,sum_abcadd r3,r3,r0brz win1st r3,sum_abcbr save
test1c  ld r0,char_cadd r0,r2,r0brnp error1ld r0,char_0not r0,r0add r0,r0,#1add r0,r0,r3brn error1ld r3,num_cnot r0,r0add r0,r0,#1add r3,r0,r3brn error1st r3,num_cld r3,sum_abcadd r3,r3,r0brz win1st r3,sum_abcbr save
win1    ld r0,lfoutlea r0,wins1puts halt
error1  lea r0,invalidputsld r0,lfoutbr try1datain2 st r0,save_r0st r2,save_r2st r3,save_r3st r7,saver7
try2    jsr cue2getcoutadd r2,r0,#0not r2,r2add r2,r2,#1getcoutadd r3,r0,#0ld r0,lfout
test2a  ld r0,char_aadd r0,r2,r0brnp test2bld r0,char_0not r0,r0add r0,r0,#1add r0,r0,r3brn error2ld r3,num_anot r0,r0add r0,r0,#1add r3,r0,r3brn error2st r3,num_ald r3,sum_abcadd r3,r3,r0brz win2st r3,sum_abcbr save
test2b  ld r0,char_badd r0,r2,r0brnp test2cld r0,char_0not r0,r0add r0,r0,#1add r0,r0,r3brn error2ld r3,num_bnot r0,r0add r0,r0,#1add r3,r0,r3brn error2st r3,num_bld r3,sum_abcadd r3,r3,r0brz win2st r3,sum_abcbr save
test2c  ld r0,char_cadd r0,r2,r0brnp error2ld r0,char_0not r0,r0add r0,r0,#1add r0,r0,r3brn error2ld r3,num_cnot r0,r0add r0,r0,#1add r3,r0,r3brn error2st r3,num_cld r3,sum_abcadd r3,r3,r0brz win2st r3,sum_abcbr save    win2    ld r0,lfoutlea r0,wins2puts halt
error2  lea r0,invalidputsld r0,lfoutbr try2
save    ld r0,lfout ld r0,saver0ld r2,save_r2ld r3,save_r3ld r7,saver7retlf .fill x000a
char_a  .fill x0041
char_b  .fill x0042
char_c  .fill x0043
char_0  .fill x0030
wins1   .stringz "Player 1 Wins."
wins2   .stringz "Player 2 Wins."
invalid .stringz "Invalid move. Try again."
sum_abc .fill #16
saver0  .fill #0
save_r2 .fill #0
save_r3 .fill #0
saver7  .fill #0.end

思路分析

程序总体设计

核心数据结构

1、显示游戏页面

首先将寄存器的值存进内存,待子函数完成任务后再将该内存的值存进寄存器,用伪操作.stringz开辟内存用来存储字符串,将Row A、Row B和Row C的石头数目也存储在内存中。

先用LEA指令将字符串的首地址存进R0,然后通过PUTS输出,用LD指令将字符o的ascll码存进R0,然后用LD指令将石头的数目存进R1,R1作为计数器,用OUT循环输出字符o,最后用LD指令将换行符的ascll码存进R0,用OUT输出。

2、用户操作

(1)输出提示

用伪操作.stringz将提示字符串存进内存中,先将用到的寄存器R0和R7的值存进内存保存起来,然后用LEA指令将字符串的首地址存进R0,用PUTS输出提示,然后将R0和R7的值恢复。

(2)用户输入

用GETC读取输入的第一个数据,然后用OUT回显,ADD指令将R0的数据转入R2,然后用NOT将R2取反,ADD将R2加一,即将R2取负,再用GETC读取输入的第二个数据,OUT回显,ADD指令将R0的数据转入R3。

(3)判断数据是否有效

用伪操作.fill将字符A、B和C的ascll码存进内存,用LD指令将相应字符的ascll码存进R0,然后ADD指令将R0和R2相加的结果存在R0,通过判断R0是否为0来判断是A、B、C或无效输入。

(4)取石头

用LD指令将字符0的ascll码存进R0,然后将R0取负,与R3相加的结果存放到R0中,然后用LD指令将石头的数目存进R3,将R0取负,与R3相加的结果存进R3,最后将R3的值存进内存。

算法流程

1、显示游戏页面

2、player操作

LC-3 汇编语言 Nim游戏相关推荐

  1. 【bzoj3150】 cqoi2013—新Nim游戏

    www.lydsy.com/JudgeOnline/problem.php?id=3105 (题目链接) 题意 在第一个回合中,第一个游戏者可以直接拿走若干个整堆的火柴.可以一堆都不拿,但不可以全部拿 ...

  2. LeetCode实战:Nim 游戏

    背景 为什么你要加入一个技术团队? 如何加入 LSGO 软件技术团队? 我是如何组织"算法刻意练习活动"的? 为什么要求团队的学生们写技术Blog 题目英文 You are pla ...

  3. POJ 1704 Georgia and Bob (Nim游戏变形)

    题目:http://poj.org/problem?id=1704 思路:Nim游戏策略,做如下转换,如果N是偶数,则两两配对,将两个数之间的格子数(距离)看做成这一堆石头的数量. 如果N是奇数,则将 ...

  4. BZOJ 3105:[cqoi2013]新Nim游戏

    BZOJ 3105:[cqoi2013]新Nim游戏 题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=3105 题目大意:在传统的Nim取石子 ...

  5. 【bzoj3105】新Nim游戏

    Portal--> bzoj3105 新Nim游戏 Solution 转化一下问题 首先看一下原来的Nim游戏,先手必胜的条件是:每堆数量的异或和不为\(0\) 所以在新的游戏中,如果要保证自己 ...

  6. 文巾解题 292. Nim 游戏

    1 题目描述 2 解题思路 这其实是一个脑筋急转弯一样的题目.先给出结论吧:如果堆中石头的数量 n 不能被 4 整除,那么你总是可以赢得 Nim 游戏的胜利. 下面是推导部分: 让我们考虑一些小例子. ...

  7. 洛谷P4301 [CQOI2013]新Nim游戏

    洛谷P4301 [CQOI2013]新Nim游戏 题目描述 传统的Nim游戏是这样的:有一些火柴堆,每堆都有若干根火柴(不同堆的火柴数量可以不同).两个游戏者轮流操作,每次可以选一个火柴堆拿走若干根火 ...

  8. 洛谷 P2197 nim游戏

    洛谷 P2197 nim游戏 题目描述 甲,乙两个人玩Nim取石子游戏. nim游戏的规则是这样的:地上有n堆石子(每堆石子数量小于10000),每人每次可从任意一堆石子里取出任意多枚石子扔掉,可以取 ...

  9. 经典数学问题:Nim游戏

    Nim游戏的数学理论论述 Nim游戏是博弈论中最经典的模型,是组合游戏(Combinatorial Games)的一种,属于"Impartial Combinatorial Games&qu ...

最新文章

  1. Python深度学习:基于PyTorch [Deep Learning with Python and PyTorch]
  2. windows启动mysql8服务_MySQL8.0服务启动(windows10)
  3. onedrive下载
  4. 鼠标右键新建菜单删除或添加项目
  5. 2010年杭电计算机研究生复试---笔试编程
  6. Linux+php+memcache+APC加速PHP网站
  7. 记录一个SpringBoot集成邮件及工具类博客
  8. php模板技术 实例
  9. Context是怎么在Go语言中发挥关键作用的
  10. 并发执行linux命令结果混乱,Shell脚本--并发执行
  11. #CSP 201909-1 小明种苹果
  12. python项目实战:实现数据可视化三维拟合
  13. 我用Python爬了点你们需要的电影,这些电影真的很不错~
  14. 使用DNSStager在DNS中隐藏Payload
  15. 字符打印流(PrintWriter)
  16. 爆裂:未来社会的 9 大生存原则
  17. jms与ActivityMQ中的简单使用
  18. 如何破解VS2015(使用秘钥)
  19. 如何实现基于Electron的截图识字App(一)
  20. C# 关于winFrom控制网页的自动登录的问题(网页刷屏器的制作原理)

热门文章

  1. 高通开发Qual FQ
  2. 三菱PLC梯形图触点比较指令(><=)为什么加D
  3. 湘潭赛Easy wuxing(递推+矩阵快速幂or DP)
  4. Sphinx匹配模式详解
  5. java class cast_Java异常ClassCastException
  6. C++中vector函数
  7. vector函数用法全解
  8. 使用伟福仿真器对IAR 8051生成的HEX文件进行仿真
  9. 金蝶K3 WISE V14.3 完整安装包(安装盘+资源盘)共两个压缩文件# 链接:https://pan.baidu.com/s/1lxGCud58s8DGKpbSrTZ-Qw 提取码:hksc
  10. 前端百题斩【010】——通俗易懂的JavaScript执行上下文