




已阅读5页,还剩11页未读, 继续免费阅读
版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
汇编语言实验报告学院:*班级:*姓名:*学号:*指导老师:*目 录实验一 斐波那契数列31.设计要求32.设计思想和实施方案论述33.课程设计中遇到的问题及解决方案54.程序流程图65.源程序及注释6实验二 统计学生成绩111.设计要求112.设计思想和实施方案论述113.典型程序模块及典型编程技巧分析114.课程设计中遇到的问题及解决方法125.程序流程图,程序清单和程序注释126.程序清单和注释13收获与体会16参考书籍:16实验一 斐波那契数列1. 设计要求用递归的方法求斐波那契的第24项(N=24),并将结果用十进制显示出来输出FIB(24)的值2. 设计思想和实施方案论述 FIB函数采用子程序递归调用方法,实现求斐波那契数列先写出高级语言中的斐波那契递归函数:Int fib(int N)If(N=1|N=0) result=1;Else result=fib(n-1)+fib(n-2);Return result;其函数为高级语言的形式,其中result=fib(n-1)+fib(n-2)隐含了几个操作可把它展开为:N=N-1;注意到这里的N是形参(局部变量)与调用程序的实参不是同一个变量Int a=fib(N)N=N-1Int b=fib(N)Result = a+b;由此可知几个重要实现地方:a) 保存现场:N在一个fib函数里面是局部变量,当系统调用子程序时需要保存这个局部变量,在返回时需要恢复:SUBT PROC NEARPUSH AXPUSH BX.POP BXPOP AX SUBT ENDP; 采用保存恢复寄存器的形式b) 参数传递:其中的N在调用fib传参时是作为实参,在被调用函数中还需要被使用,这是参数的传递,这里采用通过数据区传递参数(同全局变量)c) 返回值:最后的result在高级语言中是通过将result赋给一个临时变量(调用该函数的程序)然后释放result这个局部变量,在本程序中采用寄存器直接传递的方法,所以在Fib函数中将result赋给一个寄存器,然后不保存它,让其传递到上层调用函数中去。3. 课程设计中遇到的问题及解决方案l 遇到的问题在编写斐波那契函数的过程中主要遇到了问题是保存现场的问题,在高级语言中,对子程序调用时,系统会自动为我们保存当前程序的现场指令地址,局部变量。而在汇编中除了现场指令地址保存外,其他的工作都必须我们自己完成,所以在对子程序调用时,怎么保存当前的局部变量,怎么传递参数到将要调用的函数中去使用,都是很难理顺思路的地方。l 解决方案第一:明确哪些是局部变量,在调用完子程序返回时要恢复的。第二:局部变量作为实参,与被调用的子程序中的形参的区别。第三:确保有压栈就必须对应出栈,且系统的中断指令地址的保存与我们使用的栈是同一个栈解决方案在上面已经写过,就没有在复述了4. 程序流程图 .NN-1N-2.21Fib(2)Fib(1)Fib(N-2)Fib(N-1)Fib(N)5. 源程序及注释DATAS SEGMENT message1 db input the number ,$ NUM=18h ;修改此处获得第N项斐波那契数列值 N dw 0;用于传参的NDATAS ENDSCODES SEGMENT ASSUME CS:CODES,DS:DATASMain proc farSTART: push ds sub ax,ax push ax mov ax,DATAS mov ds,ax mov byte ptr N,NUM call FIB;调用Fib子程序 mov dx,ax ;call Output_CTLF call PrintOX;将十进制转换为十六进制输出 mov ah,1 int 21h ;等待退出屏幕 retMain endp; output CTLFOutput_CTLF proc Nearpush ax push dxmov ah,02hmov dl,0dh int 21hmov dl,0ahint 21h pop dxpop axretOutput_CTLF endp ;input value in dxPrintOX proc nearmov cl,4loop1:push cxmov cl,4rol dx,clmov ax,dxpop cxand ax,000fh cmp ax,000ahjl LessThanAadd ax,07hLessThanA:add ax,30hpush dxmov dl,almov ah,2int 21hpop dxloop loop1retPrintOX endpFIB proc near;FIB子函数push cx;cx与bx为局部变量push bxmov cx,N;使用N作为实参传参,cx为形参cmp cx,1;相当于if(N=1)jle less_equal_1dec cx;相当于N-1mov N,cx;使用N作为实参传参call FIB;FIB(N-1)mov bx,axdec cx;相当于N-1mov N,cx;使用N作为实参传参call FIB;FIB(N-1)add ax,bx;ax中保存FIB(N-1)+FIB(N-2),并且作为返回值jmp enderless_equal_1:mov ax,1;如果N=1 result=1ender:pop bxpop cxretFIB endpCODES ENDS end start实验二 统计学生成绩1. 设计要求设计10个学生的成绩分别为56、69、84、82、73、88、99、63、100和80分。试编制程序分别统计低于60分、60-69分、70-79分、80-89分、90-99分及100分的人数,并存放到S5、S6、S7、S8、S9及S10单元中。2. 设计思想和实施方案论述定义以x为数组名的含10个单元的一维数组,分别存放10个学生的成绩;定义变量S5、S6、S7、S8、S9及S10,初始化为0,以存放各成绩阶段的人数,以上均以字为存储单元长度。建立子程序SEARCH,用以查找学生成绩并进行各成绩阶段的人数统计,并在主程序中调用。其中,统计应用公式 (成绩)/10-5)*2根据成绩相s5的相对地址变化量来进行存储。3. 典型程序模块及典型编程技巧分析子程序SEARCH(统计人数) SEARCH: MOV SI, 0 NEXT: MOV AX, xSI MOV BX, 10 DIV BL MOV BL,AL SUB BX,5 SAL BX, 1 INC S5BX ADD SI, 2 LOOP NEXT RET子程序PRINTMen 人数PRINTMen: MOV AH,02H INT 21H MOV DL, MOV AH,02H INT 21H RET编程技巧:采用子程序方法,使程序更易分析,模块更清晰,利用循环和相对地址变化量来减少程序的冗余度,是其看起来精简和更易分析。4. 课程设计中遇到的问题及解决方法1、对汇编语言编程的基本结构都不会 解决方法:看书,多看几个程序,便熟悉了基本结构data segment,code segment等。2、数组的地址分配方式很糊涂,其存储单元的长度与首地址的关系 解决方法:请教老师同学,在多次练习小习题后,进行画图分析3、子程序的使用方法 解决方法:多看程序4、公式的汇编语言转换 解决方法:“心急吃不了”热豆腐,将大化小,化繁为易,一步步计算5. 程序流程图,程序清单和程序注释子程序SEARCHCX=CX-1对应的存储单元S5BX的值加1将当前地址单元的值送到AX中否子程序返回进入NEXT循环利用公式(成绩)/10-5)*2,计算出当前成绩相对于首地址的变化量,送给BXCX等于0 ?初始化相对地址变化量SI=0子程序调用开始6. 程序清单和注释DATA SEGMENT ;数据段开始x DW 56,69,84,82,73,88,99,63,100,80;定义数组,以存放学生成绩S5s DW 0 ;定义变量s5,表示分数50-59分统计结果S6 DW 0 ;定义变量s6,表示分数60-69分统计结果S7 DW 0 ;定义变量s7,表示分数70-79分统计结果S8 DW 0 ;定义变量s8,表示分数80-89分统计结果S9 DW 0 ;定义变量s9,表示分数90-99分统计结果S10 DW 0 ;定义变量s10,表示100分统计结果DATA ENDS ;数据段结束CODE SEGMENT ;代码段开始 MAIN PROC FAR ;MAIN函数声明ASSUME CS: CODE, DS: DATASTART: PUSH DS ;过程开始 SUB AX,AX PUSH AX MOV AX,DATA MOV DS, AX ;初始化BEGIN: MOV CX, 10 ;BEGIN函数开始 CALL SEARCH ;调用统计人数子程序 MOV DL,BYTE PTR S5 ADD DL,30H CALL PRINT ;将分数50-59分统计结果赋值s5并输出 MOV DL,BYTE PTR S6 ADD DL,30H CALL PRINT ;将分数60-69分统计结果赋值s6并输出 MOV DL,BYTE PTR S7 ADD DL,30H CALL PRINT ;将分数70-79分统计结果赋值s7并输出 MOV DL,BYTE PTR S8 ADD DL,30H CALL PRINT ;将分数80-89分统计结果赋值s8并输出 MOV DL,BYTE PTR S9 ADD DL,30H CALL PRINT ;将分数90-99分统计结果赋值s9并输出 MOV DL,BYTE PTR S10 ADD DL,30H CALL PRINT ;将分数100分统计结果赋值s10并输出 RET MAIN ENDP ;MAIN主程序结束SEARCH PROC NEAR ;SEARCH子程序开始 MOV SI, 0 ;初始化地址变化量为0NEXT: MOV AX, xSI MOV BX, 10 ;根据成绩计算相对S5的地址变化量 DIV BL ;计算公式(成绩)/10-5)*2送(BX) MOV BL,AL ;(BH)保持为0不变 SUB BX,5 ;只统计50分以上成绩 SAL BX, 1;(BX)*2 INC S5BX ;S5是S5,S6,S7,S8,S9和S10单元的首地址 ADD SI, 2 LOOP NEXT RETSEARCH ENDP ;SEARCH子程序结束PRINT PROC NEAR ;输出统计结果子程序 MOV AH,02H INT 21H MOV DL, MOV AH,02H INT 21H RET PRINT ENDP ;PRINT子程序结束 CODE ENDS ;代码段结束 END START 收获与体会汇编语言是一门低级语言,所以在程序设计的过程中我明显的感觉到一个词:底层!如,输入输出时要对每一位数值位进行处理,加深了对高级语言中输入输出格式的理解;子程序调用时需要自己设计分析堆栈的空间的分配情况,让我明白保存现场的意义及实现方式;使用变量时要仔细分配急度缺乏的寄存器资源,这也是程序优化的核心思想;甚至是要考虑到变量因为类型的不同储存的方式也不同,以及使用很少的指令集,自己编写出一些实用功能的函数,因为底层,指令不便于阅读所以模块化,规范化在这里体现的尤为的重要,注释及程序文档则是比不可少的,不然由几条指令变化出来的这么多功能很难再短时间内读懂。此外,对汇编程序的调试也是一大难点,由于其完全是DOS下的编译环境,而且出错时给出的
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
评论
0/150
提交评论