例1
定义一个输出字符串的OUT_STRING宏,编写一个程序,该程序使用OUT_STRING宏将两个输入的十进制数相加并输出。
.MODEL SMALL
.STACK 100H
.DATA
InMSG1 DB 'Input the first decimal number:$'
InMSG2 DB 0DH,0AH,'Input the second decimal number:$'
OutMSG DB 0DH,0AH,'The sum of the decimal numbers is $'
OUT_STRING MACRO MSG ;用于输出字符串的宏
LEA DX,MSG
MOV AH,9
INT 21H ;输出字符串
ENDM
.CODE
MAIN PROC
MOV AX,@DATA
MOV DS,AX
OUT_STRING InMSG1 ;调用宏输出InMSG1的内容
CALL INDECM ;键盘输入
MOV BX,AX ;把键盘输入的存储到BX里
OUT_STRING InMSG2 ;调用宏输出InMSG2的内容
CALL INDECM ;键盘输入
ADD BX,AX ;把第一次输入的和第二次输入的相加
OUT_STRING OutMSG ;调用宏输出OUT_STRING的内容
MOV AX,BX ;把相加后的结果存储到AX里
CALL OUTDECM ;输出AX
MOV AH,4CH
INT 21H
MAIN ENDP
INCLUDE INDECM.ASM
INCLUDE OUTDECM.ASM
END MAIN
例2
定义一个MAKE_WORD宏,它将两个8位数据组合成16位并存储在BX中,并编写一个程序,该程序将使用MAKE_WORD宏接收的10个字符存储在字数组ArayW中,并以十六进制输出。
.MODEL SMALL
.STACK 100H
.DATA
ArrayW DW 5 DUP (?)
MAKE_WORD MACRO BYT1,BYT2
PUSH CX ;把CX推入堆栈中
MOV BL,BYT1 ;把第一个参数的值给BL
MOV CL,8 ;CL存8
SHL BX,CL ;把BX左移八个位
OR BL,BYT2 ;把BYT2存到BX的低位
POP CX ;把堆栈中的CX取回来
ENDM
.CODE
MAIN PROC
MOV AX,@DATA
MOV DS,AX
MOV AH,2
MOV DL,'?'
INT 21H ;输出问号
XOR SI,SI ;初始化SI
MOV CX,5 ;CX存5,用于循环计次
MOV AH,1
@TOP1:
INT 21H ;键盘输入
MOV BL,AL ;把键盘输入的内容存到BL里
INT 21H ;键盘输入
MAKE_WORD BL,AL ;把两次键盘输入的值作为参数调用宏
MOV ArrayW[SI],BX ;把经过宏处理过的BX存入ArrayW数组
ADD SI,2 ;地址寄存器SI加2
LOOP @TOP1 ;循环五次
MOV AH,2
MOV DL,0DH
INT 21H
MOV DL,0AH
INT 21H ;输出回车
XOR SI,SI ;初始化SI
MOV CX,5 ;CX存5,用于循环次数
@TOP2:
MOV BX,ArrayW[SI] ;把ArrayW[SI]的值给BX
CALL OUTHEXA ;调用OUTHEXA
MOV DL,' '
INT 21H ;输出空格
ADD SI,2 ;SI加2
LOOP @TOP2 ;循环
MOV AH,4CH
INT 21H
MAIN ENDP
OUTHEXA PROC
PUSH CX ;cx推入堆栈中
MOV DH,4
MOV CL,4 ;右移次数存4
MOV AH,2
@OUTPUT:
MOV DL,BH ;BX的高位BH给DL
SHR DL,CL ;DL右移四个位
CMP DL,0AH
JL @NUMBER ;如果小于就跳转NUMBER
ADD DL,37H ;十六进制转回A-F
JMP @NEXT
@NUMBER:
OR DL,30H ;16进制值0-9变成'0'-'9'
@NEXT:
INT 21H ;输出
ROL BX,CL ;循环左移四个位
DEC DH ;DH减1
JNZ @OUTPUT ;如果ZF=0就跳转OUTPUT
POP CX ;cx从堆栈中取回来
RET
OUTHEXA ENDP
END MAIN
例3
使用BIG_ARRAY宏输入的7个元素。
编写一个程序,获取DW数组ArayD的最大元素值,然后打印出来。
.MODEL SMALL
.STACK 100H
.DATA
ArrayD DW 7 DUP (?)
BIG_ARRAY MACRO ARRAY,N ;定义一个宏
LOCAL @TOP,@NEXT
PUSH BX ;把BX推入堆栈
PUSH CX ;把CX推入堆栈
LEA BX,ARRAY ;取Array的地址
MOV AX,[BX] ;把ARRAY第一个元素给AX
MOV CX,N ;把N的值给CX
DEC CX ;CX减1
@TOP:
ADD BX,2 ;BX+2意味着到下一个元素
CMP [BX],AX ;比较[BX]和AX的大小
JLE @NEXT ;如果小于或等于就跳转NEXT
MOV AX,[BX] ;把AX的值替换成[BX]的值(大于的情况)相当于AX始终保持最大
@NEXT:
LOOP @TOP ;循环直到CX等于0,这次是循环七次
POP CX
POP BX ;出栈,注意顺序,从最后推入的开始出栈
ENDM
.CODE
MAIN PROC
MOV AX,@DATA
MOV DS,AX
MOV AH,2
MOV DL,'?'
INT 21H ;输出问号
MOV CX,7 ;CX存7用于计次
XOR SI,SI ;SI初始化
@INPUTD:
CALL INDECM ;调用INDECM,键盘输入
MOV ArrayD[SI],AX ;把键盘输入的存到ArrayD[SI]
ADD SI,2 ;SI加2,表示到数组的下一个元素
LOOP @INPUTD ;循环七次
MOV AH,2
MOV DL,0DH
INT 21H
MOV DL,0AH
INT 21H ;输出回车
BIG_ARRAY ArrayD,7 ;找最大的数
CALL OUTDECM ;输出
MOV AH,4CH
INT 21H
MAIN ENDP
INCLUDE INDECM.ASM
INCLUDE OUTDECM.ASM
END MAIN
例4
输入两组数(每组五个数) 输出每组的和
.MODEL SMALL
.STACK 100H
.DATA
ArrayA DW 5 DUP (?)
ArrayB DW 5 DUP (?)
SUM_ARRAY MACRO ARRAY,N
LOCAL @TOP
PUSH SI ;把SI推入堆栈
PUSH CX ;把CX推入堆栈
XOR AX,AX ;初始化AX
XOR SI,SI ;初始化SI
MOV CX,N ;把输入的N存到CX
@TOP:
ADD AX,ARRAY[SI] ;把ARRAY[SI]存到AX里
ADD SI,2 ;地址SI加2
LOOP @TOP ;循环次数取决于传入的N也就是CX
POP CX
POP SI ;从堆栈中推出
ENDM
NEWLINE MACRO
MOV AH,2
MOV DL,0DH
INT 21H
MOV DL,0AH
INT 21H ;回车
ENDM
.CODE
MAIN PROC
MOV AX,@DATA
MOV DS,AX
MOV AH,2
MOV DL,'?'
INT 21H ;输出问号
MOV CX,5 ;CX存储5,循环次数
XOR SI,SI ;SI初始化
@INPUTA:
CALL INDECM ;键盘输入
MOV ArrayA[SI],AX ;把键盘输入的存到ArrayA[SI]里
ADD SI,2 ;地址加2
LOOP @INPUTA ;循环,一共循环五次
NEWLINE ;调用NEWLINE换行
MOV DL,'?'
INT 21H ;输出问号
MOV CX,5 ;循环次数存储5
XOR SI,SI ;SI清零
@INPUTB:
CALL INDECM ;键盘输入
MOV ArrayB[SI],AX ;把键盘输入的存到ArrayB[SI]里
ADD SI,2 ;地址加2
LOOP @INPUTB ;循环
NEWLINE ;回车换行
SUM_ARRAY ArrayA,5 ;调用SUM_ARRAY吧ArrayA里面的五个元素相加
CALL OUTDECM ;输出AX
MOV AH,2
MOV DL,' '
INT 21H ;输出空格
SUM_ARRAY ArrayB,5 ;调用SUM_ARRAY吧ArrayA里面的五个元素相加
CALL OUTDECM ;调用OUTDECM
MOV AH,4CH
INT 21H
MAIN ENDP
INCLUDE INDECM.ASM
INCLUDE OUTDECM.ASM
END MAIN
例5
输入七个数,反向输出
.MODEL SMALL
.STACK 100H
.DATA
ArrayB DW 7 DUP (?)
XCHGW MACRO WRD1,WRD2 ;交换WRD1和WRD2的值
PUSH AX
MOV AX,WRD1
XCHG AX,WRD2
MOV WRD1,AX
POP AX
ENDM
.CODE
MAIN PROC
MOV AX,@DATA
MOV DS,AX
MOV AH,2
MOV DL,'?'
INT 21H ;输出问号
MOV CX,7 ;CX存储7,用于计次7
XOR SI,SI ;初始化SI
@INPUTB:
CALL INDECM ;键盘输入
MOV ArrayB[SI],AX ;把键盘输入的存到ArrayB[SI]里
ADD SI,2 ;地址寄存器SI加2
LOOP @INPUTB ;循环7次
MOV AH,2
MOV DL,0DH
INT 21H
MOV DL,0AH
INT 21H ;输出回车
MOV CX,3 ;CX存储3,用于计次
LEA SI,ArrayB ;取ArrayB的地址到SI
MOV DI,SI ;把SI给DI
ADD DI,12 ;给DI加12
@REVERSE:
XCHGW [SI],[DI] ;相当于第一次的时候是把第一个和最后一个交换
ADD SI,2
SUB DI,2 ;首尾切至下一个数
LOOP @REVERSE ;循环三次
MOV CX,7 ;循环次数存7
XOR SI,SI ;SI清零
@OUTB:
MOV AX,ArrayB[SI] ;把ArrayB[SI]给AX
CALL OUTDECM ;输出AX
MOV AH,2
MOV DL,' '
INT 21H ;输出空格
ADD SI,2 ;地址寄存器SI加2
LOOP @OUTB ;循环七次
MOV AH,4CH
INT 21H ;结束
MAIN ENDP
INCLUDE INDECM.ASM
INCLUDE OUTDECM.ASM
END MAIN