汇编语言实现打印杨辉三角
计算杨辉三角形的前n(n<=10)行,并显示在屏幕上。要求计算及显示
用子程序形式实现。其显示格式为:
1
11
121
1331
14641
15101051
CODESEGMENT
ASSUMECS:CODE,DS:CODE
org100h
START:jmpbegin
messagedb13,10,9,'InputN(N<=10):$'
errordb13,10,9,'Dataoutofrange!$'
begin:
pushcs
popds
movdx,offsetmessage
movah,9
int21h
callshur
cmpbp,10
jbegoon
movdx,offseterror
movah,9
int21h
jmpexit
goon:
movax,0e0dh
int10h
moval,0ah
int10h
pushbp
callyhsj
exit:
movah,0
int16h
movah,4ch
int21h
shurproc
pushcx
pushbx
xorbp,bp
movbx,10
movcx,2
input:
movah,0;键盘输入数据
int16h
cmpal,0dh;以回车结束输入
jzok
cmpal,'0';只允许输入0~9
jbinput
cmpal,'9'
jainput
movah,0eh;显示有效输入
int10h
subal,30h;化ASCII为HEX
cbw;字节扩展为字
xchgax,bp
mulbx;扩大10倍
addbp,ax;加一位
loopinput
ok:nop;数值结果在BP中
;恢复用到的寄存器
popbx
popcx
ret
shurendp
;输出杨辉三角的函数,接受一个栈上的参数N
;输出N阶杨辉三角
yhsj:
movbp,sp
movax,[bp+2];保存N到ax
shrax,1;N=N/2
pushax
movax,[bp+2];保存N到ax
pushax
callC;C(N,N/2)获取最后一行中间的那个值,即最大值
callgetdigit;计算该最大值的长度,如252则返回3
movcx,ax;保存最大长度到cx,用于事后格式用
xordi,di;外层循环计数di,外层循环输出每一行
jmpcp1
up1:
incdi;更新di
cp1:
cmpdi,[bp+2];测试循环条件,循环N次
jgdone1
movax,[bp+2];以下3句计算行前空格数=(N-i)*cl,cl是最大长度
subax,di
mulcl
callshowspace;输出行前空格
xorsi,si;内存循环计数si,内层循环输出一行中的每个数
jmpcp2
up2:
incsi;更新di
cp2:
cmpsi,di;测试循环条件,循环di次
jgdone2
pushsi
pushdi
callC;获取该行的位于si位置的组合数,调用C(di,si)
pushax;保存该组合数
callshow;输出该数
movax,cx;┒以下3句输出数字间间隔空格,个数=N-1
subax,1;┃
callshowspace;┚
popax;┒
callgetdigit;┃获取该组合数长度
movbx,ax;┃
movax,cx;┃
subax,bx;┃计算需要填充的空格数=最大长度-该数长度+1
addax,1;┃本来应该先填充再输出数字间空格,顺序反过来是为了左对齐
callshowspace;┚以上打括号的2段反过来是正常的顺序
jmpup2;更新内层循环
done2:;内层循环结束
movah,2;以下5句实现换行
movdl,13
int21h
movdl,10
int21h
jmpup1;更新外层循环
done1:;外层循环结束
ret2;释放函数参数使用的栈空间
;求组合数的递归函数,接受栈上的2个参数n,m(n>m)
;返回C(n,m),即n选m的个数
;算法是:
;{C(n,m)=1(nm)
;即某位置组合数等于上一行左右两数之和
C:
pushbp
movbp,sp
subsp,2;预留一个存储位置
movbx,[bp+6];保存m到bx
cmpbx,[bp+4];如果m>n返回1
jzL1
cmpbx,0;如果m=0返回1
jzL1
movax,[bp+4];保存n到ax
decax;ax=ax-1
decbx;bx=bx-1
pushbx
pushax
callC;返回上一行左边的那个数
mov[bp-2],ax;保存左肩膀上的数
movax,[bp+4];以下5句同理,返回上一行右肩膀上的数
decax
push[bp+6]
pushax
callC
addax,[bp-2];和左肩膀上的数相加得出该组合数
jmpL2
L1:
movax,1
L2:
movsp,bp
popbp
ret4;ax返回组合数
;递归以10进制输出ax
;方法很简单,就是求出余数,然后ax=ax/10
;ax=0时退出,开始逆序输出求出的各位余数
show:
movbx,10
cmpax,0
jzok1
divbl
pushax
andax,00ffh
callshow
popdx
movdl,dh
ordl,30h
movah,2
int21h
ok1:
ret
;获取一个数的长度,ax为参数,如果ax=252则返回3
;ax里是返回值
getdigit:
movbx,10
xordx,dx
next:
cmpax,0
jleok2
divbl
andax,0ffh
incdx
jmpnext
ok2:
movax,dx
ret
;输出ax个空格,参数ax,无返回值
showspace:
movbx,ax
movah,2
movdl,''
nexts:
cmpbx,0
jledones
int21h
decbx
jmpnexts
dones:
ret
CODEENDS
ENDSTART
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持毛票票。
声明:本文内容来源于网络,版权归原作者所有,内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:czq8825#qq.com(发邮件时,请将#更换为@)进行举报,并提供相关证据,一经查实,本站将立刻删除涉嫌侵权内容。