汇编练手题集二

7.将al中的第7位和第0位交换,第6位和第1位交换,第5位和第2位交换,第4位和第3位交换。
提示:其实就是将al中的各比特位逆序排列。

完整程序如下:

data segment
        array db 8 dup(0)
data ends

code segment
        assume cs:code,ds:data
main:
        mov ax,data
        mov ds,ax
       
        lea si,array
        mov bl,10000000B        ;初始测试位
        mov al,10110101B        ;设置al的值[可自己设置]

        mov cx,8
s1:     test al,bl
        jz next
        inc byte ptr [si]    ;相应位如果不为0,则置1
next:   shr bl,1
        inc si
        loop s1
          ;第一个循环体为得到逆序的[自左至右]al中各比特位的值

        lea si,array+1        ;第0位不用移位操作
        shl byte ptr [si],1    ;第1位左移1位
        inc si
        mov bl,2
        mov cx,6
s2:     push cx
        mov cl,bl
        shl byte ptr [si],cl
        inc si
        inc bl
        pop cx
        loop s2
          ;第二个循环体为第x位则左移x位,以实现逆序排列
       
        lea si,array
        mov al,0
        mov cx,8
s3:     or al,[si]    ;循环'或'操作,实现单字节数据的位逆序排列
        inc si
        loop s3

        mov ah,4ch
        int 21h

code ends
end main

 

============================================
8.已知内存source_dat单元开始连续存放若干个字型单元数据,数据个数在counts单元中存放.编制程序求这些数据中出现次数最多的数据,将出现次数及数据分别存入mostTimes_data+2和mostTimes_data单元.

完整程序如下:

data segment
        mostTimes_data dw ?  ;存放出现次数最多的数据
                       db ?  ;存放该数据出现的次数
        source_dat dw 5,2,1,5,2,10,2
        counts db ($-source_dat)/2 dup (?,?,0)
                ;分配"($-source_dat)/2"个3个字节的内存单元
                     ;每个数据的第3个内存单元存放其出现次数
data ends

code segment
        assume cs:code,ds:data
main:
        mov ax,data
        mov ds,ax

        lea si,source_dat
        lea bx,counts
        lea di,counts
       
        mov ax,[si]
        mov [di],ax
        inc byte ptr [di+2]
        add di,3
          ;以上四句将第一个数据及其出现次数存放在目的内存区
        add si,2 ;从第2个数据开始比较
       
        mov cx,offset counts-offset source_dat
        shr cx,1  ;因为一个数据占2个字节,所以除以2
        dec cx ;减1的目的是因为从第2个数据开始比较
        push cx  ;将cx进栈
        jcxz finish   ;如果只有1个数据则直接跳至标号finish处
       
s2:     push cx
        mov cx,di
        sub cx,bx
        mov al,cl
        mov cl,3
        div cl ;因为一个数据占3个字节[包括其出现次数],所以除以3
        mov cl,al
        s1: ;将从源内存区取出的数据与目的内存区中存在的数据进行逐个比较
                mov ax,[si]
                cmp ax,[bx]
                je equal ;等于则在将已知数据出现的次数加1
                add bx,3
        loop s1
        mov [di],ax
        inc byte ptr [di+2]
        add di,3
        jmp short nextdata
         ;以上四句是将一个数据存放在目的内存区中的一个新的位置中
equal:  inc byte ptr [bx+2]

nextdata:
        lea bx,counts
        add si,2
        pop cx
loop s2

finish: lea di,mostTimes_data
        lea si,counts

        mov ax,[si]
        mov [di],ax
        mov al,[si+2]
        mov [di+2],al
          ;以上四句为存放第一个数据及其出现次数[占3字节]
          ;至目的内存区[此位置存放出现次数最多的数据及其次数]
        add si,3

        pop cx  ;取出一开始进栈的值并存入cx中,以确实比较次数
lp:     mov al,[si+2]
        cmp al,[di+2]
        jle next      ;小于或等于则直接用下一个数据出现的次数进行比较
        mov [di+2],al
        mov ax,[si]   ;大于则将此时取出的数据取代存放在mostTimes_data的数据,
        mov [di],ax     ;以及取代相应出现的次数
next:   add si,3
        loop lp
       
quit:   mov ah,4ch
        int 21h

code ends
end main

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值