当前位置:文档之家› 北邮微机原理软件实验报告

北邮微机原理软件实验报告

微机原理软件实验报告实验二分支,循环程序设计一、预习题:1.十进制数0 -- 9 所对应的ASCII 码是什么? 如何将十进制数0 -- 9 在屏幕上显示出来?答:要屏显0-9的数码,可以调用02h中断,然后将要显示的数码的ASCII码存进DL 里,然后执行INT 21H就可以打印字符。

当然,若不只一个数,调用09h中断(显示字符串)更好,但要将DS:DXZ指向要显示的数字在内存中的首地址,并要求以$结束。

2.如何检验一个数为正,为负或为零? 你能举出多少种不同的方法?答:CMP X,0 检验标志位CFCF=1,X为负数CF=0接着检验ZF:ZF=1,X为零,ZF=0,X为正数二、实验目的:1.开始独立进行汇编语言程序设计;2.掌握基本分支,循环程序设计;3.掌握最简单的DOS 功能调用.三、实验内容:1.安排一个数据区,内存有若干个正数,负数和零.每类数的个数都不超过9.2.编写一个程序统计数据区中正数,负数和零的个数.四、实验源代码assume cs:code,ds:datadata segmentbuff db 1,2,3,4,5,-1,-2,-3,0,0 ;安排的数据区string db '>0:'plus db 0 ;用变量plus来存储正数的个数db 0ah,0dhstring1 db '=0:'zero db 0 ;用变量zero来存储零的个数db 0ah,0dhstring2 db '<0:'minus db 0 ;用变量minus来存储负数的个数db '$'data endscode segmentstart:movax,datamovds,axmov cx,10 ;初始化,并将CX赋为10,因为共有10个数mov dx,0 ;将计数器dx,ah初始化为0mov ah,0lea bx,buffcompare:cmp byte ptr [bx],0 ;取出一个数与0进行比较jgeplu ;大于等于0,跳至plu执行inc ah ;小于0,用ah暂存小于0的个数,ah+1jmp next ;比完后进行下一个数的比较plu: je zer ;等于0,跳至zer执行inc dl ;大于0,用dl暂存大于0的个数,dl+1jmp next ;比完后进行下一个数的比较zer: inc dh ;等于0,用dh暂存等于0的个数,dh+1next:incbxloop compare ;将dl,dh,ah分别赋值给变量plus,zero,minus,其ASCII分别加48add dl,48movplus,dladd dh,48movzero,dhadd ah,48movminus,ahmov ah,09h ;调用09h中断,将最终结果输出lea dx,stringint 21hmov ax,4c00hint 21hcode endsend start否实验截图六、实验总结及心得体会:这个实验有两个要点。

一是字符显示。

要显示数字字符,首先要把数据转换成ASCII 码,然后调用DOS功能将其显示。

其中使用09H号功能时,要特别注意每段待输出的字符串要以’$’结尾,不然无法识别串尾,输出乱码。

二是判断正负数。

本程序选用CMP指令来实现该功能。

注意与0相比时,要使用有符号数的条件跳转指令,JGE等等,在使用无符号数的条件跳转指令时,不是与0相比较。

实验三代码转换程序设计一、预习题:1.如何将输入的两个字符(0 -- 9)变为十进制或二进制数?答:两字符减去0的ASCII码(30H)后,高位数乘以十加上低位数,即变为十进制数。

2.如何将选出的最小值(二进制或十进制)变为ASCII 码再进行显示?答:将十进制数除以十,商和余数分别加上0的ASCII码后显示在屏幕上。

3.你觉得采用二进制运算还是十进制运算更适合于这个实验?答:输入的两字符为十进制数,采用十进制运算更简洁。

二、实验目的:1.掌握几种最基本的代码转换方法;2.运用子程序进行程序设计.三、实验内容:1.从键盘上输入若干两位十进制数,寻找其中的最小值,然后在屏幕上显示出来.2.两个十进制数之间的分隔符,输入结束标志自定,但要在报告中说明.3.对输入要有检错措施,以防止非法字符输入,并有适当的提示.4.将整个程序分解为若干模块,分别用子程序实现.在报告中要给出模块层次图.四、实验源代码;说明:分隔符为空格键,结束标志位?,例如:00 00 00 00? 为正确的输入hong1 macro x ;定义宏1,检测是否为数字(asc码在48到57之间)moval,byteptr[x]cmp al,48jbwrongcmp al,57jawrongendmhong2 macro x ;定义宏2,检测是否为空格(asc码为32)moval,byteptr[x]cmp al,32jnewrongendmassume cs:code,ds:data,ss:stackdata segmentbuffer0db 100 ;存放输入的字符number db 0num db 100 dup (0)min dw 99 ;初始化的最小值min=99string0 db 'input like 00 00 00 00?',0ah,0dh,'$'string1 db 0ah,0dh,'error!',0dh,0ah,'$'string2 db 0dh,0ah,'The minus number is 'result dw ?db '$'data endsstack segmentdb 50 dup (0)stack endscode segmentinput: movdx,seg buffer0movds,dx ;初始化movax,stackmovss,axmov sp,50call displaymovdx,offset buffer0mov ah,0ahint 21hmoval,numberxorah,ahmov bl,3div bladd ah,0jnzwrongmovcl,alxorch,chmovbx,offsetnummovdx,cxdec cxjcxza2 ;若只有个一个二位数,特殊处理,跳至a2a1: call check1 ;调用check1,检测是否为数字和空格loop a1a2: call check2 ;检测结束标识符?moval,numberxorah,ahmov bl,3div blmovcl,alxorch,chmovbx,offsetnumcompare:mov al,[bx] ;将asc码转化为相应的十进制sub al,48mov dl,10mul dlmov dl,[bx+1]sub dl,48xordh,dhadd ax,dxcmpmin,ax ;将其与最小值比较,若比最小值小,则将其赋给min jbe s ;若比最小值大,则不处理,进行下一位的处理movmin,axs: add bx,3loop comparemovax,minmov bl,10 ;将最小值转化为二进制。

再加3030H转化为对应的asc码,然后显示div blmovresult,axmov ah,09hadd result,3030h ;再加3030H转化为对应的asc码,显示movdx,offset string2int 21hmov ax,4c00hint 21hdisplay:mov ah,09hmovdx,offset string0int 21hretwrong: mov ah,09hmovdx,offset string1int 21hjmp inputcheck1: hong1 bxincbxhong1 bxincbxhong2 bxincbxretcheck2: hong1 bxincbxhong1 bxincbxcmp byte ptr [bx],63jnewrongretcode endsend input程序流程图:是模块层次图:程序截图:输入错误的格式报错,然后再次输入以正确的格式输入一个数字输入两个数字输入四个数字六、实验总结及心得体会:这个实验出了很多错。

一是逻辑错误,像输入一个两位的十进制,高位的是存放在低地址,地位的存放在高地址,刚开始弄反了,导致结果出错。

二是语法错误,[BX]前面没指明类型,加byte ptr或word ptr解决。

另外在进行十进制转换时,很繁琐,实际上可以直接比较其ASC码值,这样程序将精炼很多。

实验四子程序设计一、实验目的:1.进一步掌握子程序设计方法;2.进一步掌握基本的DOS 功能调用.二、实验内容:1.从键盘上输入某班学生的某科目成绩.输入按学生的学号由小到大的顺序输入.2.统计检查每个学生的名次.3.将统计结果在屏幕上显示.4.为便于观察,输入学生数目不宜太多,以不超过一屏为宜.输出应便于阅读.尽可能考虑美观.5.输入要有检错手段.三、预习题:1.如何确定一个学生在这门科目中的名次?答:通过比较科目成绩,交换在数据区中的位置来实现,最后的位置即为科目名次。

2.你觉得输入结束后,采用什么方法进行比较以得到学生的名次最为简单?答:排序运用起泡排序算法较为简单,两两比较相邻成绩,如果不是从大到小的顺序则交换,直到没有反序的记录。

3.准备好模块层次图.4.给出输出显示的形式.答:RANK NUM SCORE,每行依名次显示排名、学号、成绩。

四、实验源代码assume cs:code,ds:data,ss:stackdata segmentbuffer db 30 ;输入字符存放的内存区number db 0info db 30 dup (0)string1 db 0ah,0dh,'input your number,name and score like"01 wang 98" ps.100=fu',0ah,0dh,'$' string2 db 0ah,0dh,'error!',0dh,0ah,'$'string3 db 'rank no name score',0ah,0dhstudent db 220 dup (32) ;用sudent开始的内存区存放所有的输入信息eg db 22 dup (32)totalnumberdw 0 ;记录总的输入学生人数statictotaldw 0 ;记录总的输入学生人数address dw 0circlenumberdw 0data endsstack segmentdb 100 dup (0)stack endscode segmentinit: movdx,seg buffer ;初始化movds,dxmovdx,stackmovss,dxmov sp,100movdx,offset buffermovaddress,offset studentadd address,2input: mov ah,09h ;调用中断,开始输入movdx,offset string1int 21hmovdx,offset buffermov ah,0ahint 21hmovbx,offset infomovcl,numberxorch,chadd cx,0jz compare ;当敲下回车时,跳至compare,开始排序call datacmp ;检测前两位学号是否输入正确call datacmpcall spacecmp ;检测中间是否为空格键sub cx,6s1: call stringcmploop s1 ;检测姓名部分是否全部为字符call spacecmpcall fullcmp1 ;检测成绩输入是否正确,注意满分用fu表示call fullcmp2 ;检测成绩输入是否正确,注意满分用fu表示movax,seg buffermoves,axmovsi,offset infomovcl,numberxorch,chsub cx,3movdi,addresscldrep movsb ;将buffer内的内容复制到student的内存区add si,1add address,16movdi,addressmov cx,2cldrep movsbadd address,6inctotalnumber ;记录总的输入学生人数incstatictotaljmp inputcompare:movdx,offset student ;排序部分,采用冒泡排序,关键处movbx,dxdectotalnumbermovcx,totalnumberjcxzspecialcase ;当只有一个学生的信息时,特殊处理:直接赋给student内存区,输出s3: movbx,dxmovtotalnumber,cx ;将cx保存在totalnumber中s4: movcirclenumber,cx ;将内层的cx保存在circlenumber中mov ah,[bx+18]cmp ah,[bx+40]ja s5jb exchangemov ah,[bx+19]cmp ah,[bx+41]jb exchanges5: add bx,22loop s4movcx,totalnumber ;恢复cx,继续循环,直至比较完毕loop s3display:decstatictotalmovcx,statictotalmovbx,offset studentmov al,49s6: mov byte ptr [bx],almov word ptr [bx+20],0a0dhinc aladd bx,22loop s6mov byte ptr [bx],almov byte ptr [bx+20],36 ;后期处理,将排序后的学生信息输出movdx,offset string3mov ah,09hint 21hmov ax,4c00hint 21hmov byte ptr [bx],49mov byte ptr [bx+20],36movdx,offset string3mov ah,09hint 21hmov ax,4c00hint 21hexchange: ;若后面的数大于前面的数,则交换两个学生的信息(22个字节)movdi,offsetegmovsi,bxmov cx,22cldrep movsbmovdi,bxmovsi,diadd si,22mov cx,22cldrep movsbmovsi,offsetegmovdi,bxadd di,22mov cx,22cldrep movsbmovcx,circlenumber ;将内层的cx恢复出来jmp s5datacmp proc ;数字检测模块,检测是否为数字cmp byte ptr [bx],48jb wrongcmp byte ptr [bx],57ja wrongincbxretdatacmpendpfullcmp1 proc ;成绩检测模块,并包含特殊字符(f)的检测cmp byte ptr [bx],102je s8cmp byte ptr [bx],48jb wrongcmp byte ptr [bx],57ja wrongretfullcmp1 endpfullcmp2 proc ;成绩检测模块,并包含特殊字符(u)的检测cmp byte ptr [bx],117je s9cmp byte ptr [bx],48jb wrongcmp byte ptr [bx],57ja wrongs9: incbxretfullcmp2 endpspacecmpproc ;空格检测模块,检测是否为空格cmp byte ptr [bx],32jne wrongincbxretspacecmpendpwrong: mov ah,09h ;错误信息显示模块movdx,offset string2int 21hjmp inputstringcmpproc ;字符检测模块,检测是否为小写字母cmp byte ptr [bx],122ja wrongcmp byte ptr [bx],97jbextracmps2: incbxretstringcmpendpextracmp:cmp byte ptr [bx],90 ;字符检测模块,检测是否为大写字母ja wrongcmp byte ptr [bx],65jb wrongjmp s2code endsend init总流程检测模块排序模块流程图内循环cx=totalnumberbx=offset studentcx=totalnumberbx=offset studentcx=totalnumberbx=offset studentcx=totalnumberbx=offset studentcx=totalnumberbx=offset student外循环cx=totalnumberbx=offset student程序截图输入错误信息输入真确信息六、实验六、实验总结与心得体会对学生成绩的排序,本实验采用的是冒泡排序,共有内外两层循环,但在汇编中只有CX一个计数器,所以关键是在进行内层循环之前一定要保存CX,内存循环结束后要恢复CX,另外,在内存循环中交换时采用了MOVSB指令,此指令也要用到CX,故本实验需要两次保存CX,两次恢复CX,分别用了totalnumber和statictotal两个变量。

相关主题