汇编语言实现快速冒泡排序

DATAS SEGMENT
    DATA DB 24,18,-8,-16,66,56,86,6,10,98
    COUNT DB 10,10
DATAS ENDS
CODES SEGMENT
    ASSUME CS:CODES,DS:DATAS,ES:DATAS
START:
    MOV AX,DATAS
    MOV DS,AX
    MOV ES,AX
    MOV BL,1  ;改进版本,用BL来检验是否排序完成,减少循环次数
LOOP1: 
        CMP BL,0 
JE DATAOUT ;ZF=1,若相等或为0,则跳转
XOR BL,BL ;用逻辑异或将BL清零 
MOV CL,COUNT ;COUNT用于外层的计数 
DEC CL ;CL减一,CL用于内层的计数 
PUSH CX ;将CX压入堆栈 
LEA DI,DATA ;将数据段首地址赋值给DI 
LOOP2: 
        MOV AL,[DI] 
CMP AL,[DI+1] ;将前一个数与后一个数比较 
JLE LOOP3 ;ZF=1或SF!=OF 若前一个数小于或等于后一个数,则跳转到LOOP3
XCHG [DI+1],AL ;前者大于后者,则交换两数
MOV [DI],AL ;如果前一个数字大于后一个数字,则交换 
MOV BL,1 
LOOP3: 
        INC DI  ;指针加一
LOOP LOOP2 ;循环L00P2,直到CX==0成立 
POP CX ;将CX从堆栈中弹出 
MOV COUNT,CL ;改变外层计数器的值 
JMP LOOP1 
DATAOUT:
        MOV CL,10 ;开始数据输出 
LEA DI,DATA ;载入数据段(数组)首地址 
NEXT:
       MOV AX,0 ;输出下一个数 
MOV BH,2 ;输出的数字之间的空格 
MOV AL,[DI] ;取数 
CMP AL,0 
JGE NON ;如果是非负数,则跳至NON 
NEG AL ;若是负数,将AL中的负数取补转成对应的正数 
PUSH AX ;INT 21H 中断将会有一个返回值 
MOV AH,2 ;同时显示负数的标记‘-’ 
MOV DL,'-' ;注意这个时候 AX 的值会因为 21H中断的调用而改变, 所以先要保存起来 
INT 21H ;若是负数,在屏幕上显示‘-’号 
POP AX ;某些中断之后AX会改变 
NON:    XOR AH,AH ;将AH清零
DIV COUNT+1 ;除以10取十位 
MOV DH,AH ;AH是余数,AL是商(如果是个位数,则AL为零) 
CMP AL,0 
JE SINGLE ;如果AL为零(个位数),则跳转到DIR,直接输出十位数 
ADD AL,30H ;将数字转换成ASC码 
MOV DL,AL ;数字放入DL,在屏幕输出 
MOV AH,2 
INT 21H ;显示十位上的数值 
SINGLE:
        MOV AL,DH ;将余数(个位数)放入AL 
XOR AH,AH ;将AH清零 
ADD AX,3030H 
MOV DL,AL ;所以最好在显示时判断是否是大于100或者小于100再根据判断结果来处理 DIV 
OUTP:MOV AH,2 ;显示输出功能
INT 21H ;显示个位数 
DEC BH  ;BH减一
JZ XT   ;若相等或为0,则跳转
MOV DL,BL ;BL为零,屏幕输出空格 
JMP OUTP 
XT:     DEC CL ;输出数组下一个 
JZ DONE ;如果ZF标志位为零(CL为零),则程序完成 
INC DI ;数组指针+1 
JMP NEXT ;继续输出数组下一个数 
DONE:   MOV AH,1 ;键盘输入并回显功能,目的是使程序输出窗口暂停,以便看到输出结果
INT 21H  
MOV AH,4CH ;带返回码结束功能
INT 21H ;返回系统 
CODES ENDS 
END START
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值