?? rank.asm
字號:
;數據段設置
DATA SEGMENT
GRADE DW 50 DUP( )
RANK DW 50 DUP( )
ENTER DB 'Grades:',24H ;提示用戶輸入成績
ERROR DB 13,10,'Error!',13,10,24H ;用戶輸入的格式出錯
SHOW DB 'Rank: ',24H
COUNT DW 0 ;統計輸入的成績個數
CR DB 13,10,24h ;換行
DATA ENDS
;*******************************************************************************
;堆棧段設置
STACK SEGMENT STACK
DB 400 DUP(0) ;初始化堆棧大小
STACK ENDS
;*********************************************************************************
;代碼段設置
CODE SEGMENT
ASSUME CS:CODE,DS:DATA,SS:STACK
START:
MOV AX,DATA
MOV DS,AX
MOV ES,AX ;ES = AS
CALL INPUT ;調用INPUT
CALL RANKP ;調用RANKP
CALL OUTPUT ;調用OUTPUT
MOV AH,01H
INT 21H ;按任意鍵退出
MOV AX,4C00H
INT 21H ;退出程序
;******************************************************************************
;INPUT程序段
;以學號為序從鍵盤輸入一個班的學生成績,各個成績之間 用逗號格開,最后以回車符結束。
;然后把一個班的成績存入grade數組。
INPUT PROC NEAR
LEA DX,ENTER
MOV AH,9
INT 21H ;提示用戶輸入
MOV SI,0
MOV COUNT,0 ;將輸入用戶的輸入個數置0
_ENTER: ;對用戶的輸入進行監視,對錯誤輸入立即進行出錯處理
CALL DECIBIN ;調用DECIBIN ;對用戶輸入進行處理
INC COUNT
CMP DL,',' ;與','比較,相同則保存成績,不同出錯
JE _STORE
CMP DL,0DH ;與回車鍵進行比較,回車則成績輸入結束
JE _ENDENTER
JNE _ERROR ;出錯處理:顯示出錯信息
_STORE: ;保存成績
MOV GRADE[SI],BX
ADD SI,2
JMP _ENTER
_ERROR:
LEA DX,ERROR
MOV AH,9
INT 21H
_ENDENTER: ;用戶結束成績輸入
MOV GRADE[SI],BX
MOV DX,OFFSET CR ;換行
MOV AH,9
INT 21H
RET
INPUT ENDP
;*******************************************************************************************
;RANKP程序段
;從grade數組取得一個班的成績,以學號為序計算出該班每個學生的名次存入rank數組。
;算法為:一個學生的名次等于成績高于該生的學生人數加1
RANKP PROC NEAR
MOV DI,COUNT
MOV BX,0
_LOOP:
MOV AX,GRADE[BX] ;取學生成績
MOV WORD PTR RANK[BX],0 ;初始化RANK[BX]的值為0
MOV CX,COUNT
LEA SI,GRADE ;第一個學生的成績
_NEXT1:
CMP AX,[SI] ;比較兩個成績
JG _JUMP ;成績大于被比較的跳過
INC WORD PTR RANK[BX]
_JUMP:
ADD SI,2 ;取下一個被比較成績的地址
LOOP _NEXT1
ADD BX,2 ; 下一個成績
DEC DI ;未比較成績個數減1
JNE _LOOP
RET
RANKP ENDP
;******************************************************************************
;OUTPUT程序段
;從rank數組取得一個班的學生名次。把一個班的學生名次以學號為序在終端顯示出來
;調用子模塊binidec,以便把rank數組中的二進制數轉成十進制數并在終端上顯示出來.調用子模塊crlf完成回車,換行功能.
OUTPUT PROC NEAR
LEA DX,SHOW
MOV AH,09H
INT 21H
MOV SI,0
MOV DI,COUNT
_NEXT2:
MOV BX,RANK[SI] ;將成績保存到BX中
CALL BINIDEC ;調用BINIDEC
CMP DI,1 ;將剩余的成績個數與1比較,若為1則不顯示','
JE _NOCOMMA
MOV DL,','
MOV AH,02H
INT 21H ;顯示','
_NOCOMMA:
ADD SI,02H ;取下一個成績名次
DEC DI
JNZ _NEXT2
MOV DX,OFFSET CR ;換行
MOV AH,9
INT 21H
RET
OUTPUT ENDP
;******************************************************************************
;DECIBIN程序段
;從鍵盤取得一個十進制數。把該數轉換成二進制數并存入BX寄存器中。
DECIBIN PROC NEAR
MOV BX,0
_CATCH:
MOV AH,01H
INT 21H
MOV DL,AL
SUB AL,30H
JL _ENDCHANGE ;小于則結束SFVOF=1
CMP AL,39H
JG _ENDCHANGE ;大于則結束
CBW
XCHG AX,BX ;AX與BX值交換
MOV CX,10
MUL CX ;無符號數乘法指令,(AX)<----(AL)*(CX)
XCHG AX,BX
ADD BX,AX ;(BX)<------(BX)+(AX)
JMP _CATCH
_ENDCHANGE:
RET
DECIBIN ENDP
;******************************************************************************
;BINIDEC程序段
;把bx寄存器中的二進制數轉換成10進制數,并在終端屏幕上顯示出來。調用dec_div來作除法運算并顯示字符。
BINIDEC PROC NEAR
PUSH BX
PUSH CX
PUSH SI
PUSH DI ;壓棧
MOV CX,10
CALL DEC_DIV ;調用DEC_DIV
MOV CX,1
CALL DEC_DIV ;調用DEC_DIV
POP DI
POP SI
POP CX
POP BX ;出棧
RET
BINIDEC ENDP
;******************************************************************************
;DEC_DIV程序段
;把bx中二進制數除以相應的十的冪,并在屏幕上顯示一位商。余數保存在bx寄存器中。
DEC_DIV PROC NEAR
MOV AX,BX
MOV DX,0
DIV CX
MOV BX,DX
MOV DL,AL
ADD DL,30H
MOV AH,02H
INT 21H ;顯示
RET
DEC_DIV ENDP
CODE ENDS
END START
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -