1、汇编语言程序设计期末大作业:编写一完整的汇编语言源程序,实现从键盘输入一个班(不少于 10 人)的学生记录(学号:8 位数字、姓名:不多余 10 个英文字符,语文:0-100 的整数、数学:0-100 的整数、英语:0-100 的整数)后,(1) 将输入的记录保存在 C 盘根目录下名为 stuscore.dat 的文件中;(2) 按照各科成绩总分先高后低的顺序输出全部学生记录和排名顺序;(3) 输出总分高于班平均总分的全部学生记录。要求: 元月 4 日前提交一份纸质报告(班长统一收齐) 。 大作业格式:1. 标题: 汇编语言程序设计期末大作业 2. 作业题目: (上述)3. 算法分析(流程图)
2、4. 实现代码(必须含注释)5. 实验结果(汇编、连接、运行的截图)6. 总结代码实现student struct ;定义结构Snumber db 11,0,11 dup(?)Sname db 11,0,11 dup(?)English db 4,0, 4 dup(?)Chinese db 4,0, 4 dup(?)Math db 4,0, 4 dup(?)Sum db 4,0, 4 dup(?)student ends;数据段data segmentmessMenu db -The Homework of Assembler-$messMenu1 db -Name:TU LIN No:800
3、0110028-$messNext db -$messName db Please input the student name()SumRank db 0, 1, 2, 3, 4, 5, 6, 7, 8, 9FName db C:StuScore.dat, 0;文件FileHandle dw ?;文件句柄EndOfFile dw 0ffhOtherLine db 0ah, 0dh, $FileSpace db “ “data ends;堆栈段stack segmentdb 100h dup(?)stack ends;代码段code segmentassume cs:code,ds:data,
4、ss:stackstart: mov ax,datamov ds,ax ;将数据段首地址传给 dsmov ax,stackmov ss,ax ;将堆栈段首地址传给 ssmov sp,0call Endlinelea dx,messMenumov ah,09hint 21hcall Endlinelea dx,messMenu1mov ah,09hint 21hcall Endlinelea si,Stu ;取 student 的首地址给 simov cx,10InputStu:call GetStudentlea dx,messNextmov ah,09hint 21hadd si,50loo
5、p InputStu ;输出循环结束lea si,Stucall GetEnglishScore call GetChineseScorecall GetMathScore call Stop ;程序运行停止一下,按回车键继续执行call Writetofilecall stopcall SumAveragecall GetSumcall GetAddresscall SortStudentcall Stop ;程序运行暂停一下,按回车键,继续执行call ShowStumov ah,4chint 21h;=;子程序名:GetStudent;功能:录入学生信息;=GetStudent proc
6、 nearpush sipush dxpush axpush cx ;子程序保护现场lea dx,messNamemov ah,9int 21hlea dx,si.Snamemov ah,0Ahint 21hcall Endlinelea dx,messNummov ah,9int 21hlea dx,si.Snumbermov ah,0Ahint 21hcall Endlinelea dx,messEnglishmov ah,9int 21hlea dx,si.Englishmov ah,0Ahint 21hcall Endlinelea dx,messChinesemov ah,9int
7、21hlea dx,si.Chinesemov ah,0Ahint 21hcall Endlinelea dx,messMathmov ah,9int 21hlea dx,si.Mathmov ah,0Ahint 21hcall Endlinepop cxpop axpop dxpop siretGetStudent endp ;=;子程序名:TureShow;功能辅助子程序 ShowStu,用于输出字符串;=TureShow proc nearpush dx ;保护相关寄存器push cxpush bxpush axmov bx,dx ;将 bx 指向缓存区的地址xor cx,cxmov c
8、l,bx+1 ;cl 存放了缓存区录入的字符数LoopTS:mov dl,bx+2 ;从第三个偏移地址开始显示mov ah,2 ;调用单个字符输出中断int 21hinc bxloop LoopTSpop axpop bxpop cxpop dxretTureShow endp;=;子程序名:ShowStu;功能:显示学生信息记录;= ShowStu proc nearpush cxpush axpush dxpush sipush di ;保护现场call Endlinelea di,SumScorelea bx,StudAddressmov cx,10Loop1: mov si,word
9、ptrbx lea dx,mess1mov ah,09hint 21h lea dx,si.Snamecall TureShowcall MessTb ;输出 1 个 Tab 用于排序对齐lea dx,mess2mov ah,09hint 21hlea dx,si.Snumbercall TureShowcall MessTb ;输出 1 个 Tab 用于排序对齐lea dx,mess3mov ah,09hint 21hlea dx,si.Englishcall TureShowcall MessTb ;输出 1 个 Tab 用于排序对齐lea dx,mess4mov ah,09hint 21
10、hlea dx,si.Chinesecall TureShowcall MessTb ;输出 1 个 Tab 用于排序对齐lea dx,mess5mov ah,09hint 21hlea dx,si.Mathcall TureShowcall MessTb ;输出 1 个 Tab 用于排序对齐lea dx,messSumScoremov ah,09hint 21hmov ax,dicall Outputcall Endlineadd bx,2add di,2loop Loop1lea dx,messNextmov ah,09hint 21hpop dipop sipop dxpop axpop
11、 cxretShowStu endp ;=;子程序名:Endline;功能:回车换行;=Endline proc nearpush ax ;保护相关寄存器push dxpush cxmov ah,2 ;回车mov dl,0ahint 21hmov ah,2 ;换行mov dl,0dhint 21hpop cxpop dxpop axretEndline endp;=;子程序名 GetEnglishScores:;功能:将得到的指定个学生的分数以十进制保存到 EnglishScore 缓冲区中;=GetEnglishScore proc nearpush di ;保护相关寄存器push sipu
12、sh dxpush cxpush bxpush axpush bplea si,Stu ;使 si 指向第一个学生的偏移地lea bp,EnglishScore ;使 bp 指向以十进制存学生分数的地址mov cx,10 ;共有指定个学生LoopScores0:push cx ;保护外循环的 CX 值lea bx,si.English ;使 bx 指向学生字符分数缓冲区xor di,dixor cx,cxmov cl,bx+1 ;学生字符分数缓冲区的字符数即使循环次数LoopScore0:mov al,bx+2 ;从第三个偏移地址开始sub al,30h ;得到一个十进制值xor ah,ahx
13、chg ax,di ;使其暂存到 di,且将高位 di 的值乘 10push si ;保护寄存器的原值push dxmov si,10mul si ;将 si 乘 10,乘积低位保存在 axpop dxpop sixchg ax,di ;将原来 di 中低位的值与高位的值 ax 交换回来add di,ax ;至此又录入一位十进制数inc bxloop LoopScore0mov ax,dimov ds:bp,al ;将得到的十进制分数存入保存十进制分数缓冲区EnglishScore 中add si,50 ;使 di 指向下一个学生的偏移地址inc bp ;使 bp 指向下一个保存十进制分数缓冲
14、区的下一个单元,以保存下一个学生的分数pop cx ;弹出外循环的 CX 值loop LoopScores0pop bppop axpop bxpop cxpop dxpop sipop diretGetEnglishScore endp;=;子程序名 GetChineseScore:;功能:将得到的指定个学生的分数以十进制保存到 ChineseScore 缓冲区中;=GetChineseScore proc nearpush di ;保护相关寄存器push sipush dxpush cxpush bxpush axpush bplea si,Stu ;使 di 指向第一个学生的偏移地lea
15、 bp,ChineseScore ;使 bp 指向以十进制存学生分数的地址mov cx,10 ;共有指定个学生LoopScores1:push cx ;保护外循环的 CX 值lea bx,si.Chinese ;使 bx 指向学生字符分数缓冲区xor di,dixor cx,cxmov cl,bx+1 ;学生字符分数缓冲区的字符数即使循环次数LoopScore1:mov al,bx+2 ;从第三个偏移地址开始sub al,30h ;得到一个十进制值xor ah,ahxchg ax,di ;使其暂存到 si,且将高位 si 的值乘 10push si ;保护寄存器的原值push dxmov si
16、,10mul si ;将 si 乘 10,乘积低位保存在 axpop dxpop sixchg ax,di ;将原来 si 中低位的值与高位的值 ax 交换回来add di,ax ;至此又录入一位十进制数inc bxloop LoopScore1mov ax,dimov ds:bp,al ;将得到的十进制分数存入保存十进制分数缓冲区ChineseScore 中add si,50 ;使 di 指向下一个学生的偏移地址inc bp ;使 bp 指向下一个保存十进制分数缓冲区的下一个单元,以保存下一个学生的分数pop cx ;弹出外循环的 CX 值loop LoopScores1pop bppop
17、axpop bxpop cxpop dxpop sipop diretGetChineseScore endp;=;子程序名 GetMathScore:;功能:将得到的指定个学生的数学分数以十进制保存到 MathScore 缓冲区中;=GetMathScore proc nearpush di ;保护相关寄存器push sipush dxpush cxpush bxpush axpush bplea si,Stu ;使 di 指向第一个学生的偏移地lea bp,MathScore ;使 bp 指向以十进制存学生分数的地址mov cx,10 ;共有指定个学生LoopScores2:push cx
18、 ;保护外循环的 CX 值lea bx,si.Math ;使 bx 指向学生字符分数缓冲区xor di,dixor cx,cxmov cl,bx+1 ;学生字符分数缓冲区的字符数即使循环次数LoopScore2:mov al,bx+2 ;从第三个偏移地址开始sub al,30h ;得到一个十进制值xor ah,ahxchg ax,di ;使其暂存到 si,且将高位 si 的值乘 10push si ;保护寄存器的原值push dxmov si,10mul si ;将 si 乘 10,乘积低位保存在 axpop dxpop sixchg ax,di ;将原来 si 中低位的值与高位的值 ax 交
19、换回来add di,ax ;至此又录入一位十进制数inc bxloop LoopScore2mov ax,dimov ds:bp,al ;将得到的十进制分数存入保存十进制分数缓冲区MathScore 中add si,50 ;使 di 指向下一个学生的偏移地址inc bp ;使 bp 指向下一个保存十进制分数缓冲区的下一个单元,以保存下一个学生的分数pop cx ;弹出外循环的 CX 值loop LoopScores2pop bppop axpop bxpop cxpop dxpop sipop diretGetMathScore endp;=;子程序名:Writetofile;功能:用于创建文
20、件并且存储学生信息;=Buildfile :push axpush cxpush dxmov ah, 3chmov cx, 00lea dx, FNameint 21hjc CreateFileErrormov FileHandle, axjmp CreateFileOkCreateFileError:mov ah, 09hmov dx, offset CreateFileErrorint 21hCreateFileOk:pop dxpop cxpop axretWriteToFile:push axpush bxpush cxpush dxpush dipush silea di, si.S
21、Namemov dx, diadd dx, 2mov cl, di+1mov ch, 0mov bx,FileHandlemov ah, 40hint 21hjc WriteFileErrorcall WriteSpacelea di, si.SNumbermov dx, diadd dx, 2mov cl, di+1mov ch, 0mov bx, FileHandlemov ah, 40hint 21hjc WriteFileErrorcall WriteSpacelea di, si.ChineseScoremov dx, diadd dx, 2mov cl, di+1mov ch, 0
22、mov bx, FileHandlemov ah, 40hint 21hjc WriteFileErrorcall WriteSpacelea di, si.MathScoremov dx, diadd dx, 2mov cl, di+1mov ch, 0mov bx, FileHandlemov ah, 40hint 21hjc WriteFileErrorcall WriteSpacelea di, si.EnglishScoremov dx, diadd dx, 2mov cl, di+1mov ch, 0mov bx, FileHandlemov ah, 40hint 21hjc Wr
23、iteFileErrorcall WriteSpacelea di, si.SumScoremov dx, diadd dx, 2mov cl, di+1mov ch, 0mov bx, FileHandlemov ah, 40hint 21hjc WriteFileErrorcall WriteEndLinejmp WriteFileOkWriteFileError:lea dx,WriteFileErrormov ah, 09hint 21hWriteFileOk:pop sipop dipop dxpop cxpop bxpop axret;*WriteSpace:mov cx, 2le
24、a dx, FileSpacemov bx, FileHandlemov ah, 40hint 21hret;*WriteEndLine:mov cx, 2lea dx, OtherLinemov bx, FileHandlemov ah, 40hint 21hretCloseFile:mov ah, 40hmov bx, FileHandlemov cx, 2lea dx, EndOfFileint 21hmov ah, 3ehmov bx, FileHandleint 21hret;=;子程序名:GetSum;功能:用于计算出每个学生的各科成绩的总分;=GetSum proc nearpu
25、sh axpush dipush sipush bxpush cxlea di,EnglishScorelea si,SumScoremov cx,10mov al,0LoopSum:mov ah,0mov al,dimov word ptrsi,axinc diadd si,2loop LoopSumlea di,ChineseScorelea si,SumScoremov cx,10mov al,0LoopSum1:mov ah,0mov al,diadd word ptrsi,axinc diadd si,2loop LoopSum1lea di,MathScorelea si,SumS
26、coremov cx,10mov al,0LoopSum2:mov ah,0mov al,diadd word ptrsi,axinc diadd si,2loop LoopSum2pop cxpop bxpop sipop dipop axretGetSum endp;=;子程序名:SumAverage;功能:用于计算出平均成绩,并输出总分高于平均分的学生记录;=SumAverage proc nearpush axpush bxpush cxpush dxpush simov cl, NumbersOfStudentmov ch, 0mov bx, cxmov ax, 0mov dx, 0
27、mov si, offset SumScoreAverageLoop:add ax, word ptr siadc dx, 0add si, 2loop AverageLoopdiv bxmov Average, ax;输出高于平均成绩的同学mov dx, offset ShowBigThanAveragemov ah, 09hint 21hmov cl, SNumbermov ch, 0mov di, 0mov si, 0ShowBigThanAverage:mov ax, SumScoresicmp ax, Averagejl ShowBigOkmov dl, SumRankdimov a
28、l, type studentmul dlmov bx, axcall Outputadd si, 2inc diloop ShowBigThanAverageShowBigOk:mov dx, offset OtherLinemov ah, 09hint 21hpop sipop dxpop cxpop bxpop axretSumAverage endp;=;子程序名:Output;功能:将 ax 中的二进制以十进制形式输出;=Output proc nearpush dipush bxpush axpush dxlea di,Bufadd di,6mov byte ptrdi,$mov
29、bx,10CHANGE:dec dimov dx,0div bxadd dl,30hmov byte ptrdi,dlcmp ax,0jnz CHANGEmov dx,dimov ah,09hint 21hpop dxpop axpop bxpop diretOutput endp;=;子程序名:GetAddress;功能:将指定个学生的偏移地址顺序保存到 StudAddress;=GetAddress proc nearpush si ;保护相关寄存器push bxpush cxlea si,Stu ;使 di 指向第一个学生的偏移地址lea bx,StudAddress ;使 bx 指向存
30、学生偏移地址的缓冲区mov cx,10 ;共有指定个学生LoopAdd:mov word ptrbx,word ptr siadd bx,2 ;使 bx 指向存学生偏移地址的缓冲区的下一个地址add si,50 ;使 di 指向下一个学的生偏移地址loop LoopAddpop cxpop bxpop diretGetAddress endp;=;子程序名:SortStudent;功能:根据学生分数进行排序;用冒泡法根据学生分数对分数从大到小排序;同时将对应的偏移地址进行排序;=SortStudent proc nearpush dxpush cxpush bxpush axpush dipu
31、sh simov cx,10dec cxLoopChange0:push cx ;保护外循环的 CX 值lea bx,SumScore ; bx 指向学生分数偏移地址lea si,StudAddress ;si 指向存学生偏移地址的地址LoopChange1: ;将学生分数和下一个学生分数分别送入al,dl 并比较大小 ;若当前学生分数小于下一个分数要交换其分数 mov dx,word ptrbx+2 ;此分数对应的学生的偏移地址mov ax,word ptrbx cmp ax,dx ja EndExchange ;若大于则转而比较下两个分数值;交换偏移地址mov ax,word ptr si
32、+2 ;指定向 ax 中传入 2 个字节数据mov dx,word ptr simov si,axmov si+2,dx;交换分数值mov ax,word ptrbx+2mov dx,word ptrbxmov word ptrbx,axmov word ptrbx+2,dxEndExchange:add si,2 ;指向下一个学生偏移地址的地址add bx,2 ;指向下一个存学生分数的地址loop LoopChange1pop cx ;保护外循环的 CX 值loop LoopChange0pop sipop dipop axpop bxpop cxpop dxretSortStudent e
33、ndp;=;子程序名:MessTb;功能:输出 1 个 Tab 键;=MessTb proc nearpush dx ;保护相关寄存器push axlea dx,MessTab ;指向输出 1 个 Tab 键缓冲区mov ah,9 ;调用字符串输出程序int 21hpop axpop dxretMessTb endp;=;子程序名:Stop;功能是让程序停止运行一下,输入回车键继续执行;=Stop proc nearpush ax ;保护相关寄存器push dxpush cxmov ah,1 ;回车int 21hpop cxpop dxpop axretStop endpcode endsend start