参考: 《汇编语言》 王爽 第7章
1. and和or指令,与[bx+idata]
and和or,就不多说了。
[bx+idata] 这样写是可以的,某些情况下,比较方便。
[bx+idata] 也可以写成 idata[bx]
直接见例子: 把’ABcde‘ 跟 ‘fGHig’ 都改成大写(ASCII中大写字母与小写字母二进制中,只有第五位不同,大写字母是0,小写字母是1)
- assume cs:code,ds:data
- data segment
- db 'ABcde'
- db 'fGHIg'
- data ends
- code segment
- start: mov ax,data
- mov ds,ax
- mov bx,0
- mov cx,4
- mov al,00100000b
- s: or [bx],al
- or [5+bx],al ;[5+bx]也可以写成5[bx]
- inc bx
- loop s
- mov ax,4c00H
- int 21H
- code ends
- end start
2. si,di,与[bx+si],[bx+di],[bx+si+idata],[bx+di+idata]
si与di,除了不能像bx一样分成bh,bl,其他与bx一样。如 mov ax,[si] 等等
[bx+si],[bx+di],[bx+si+idata],[bx+idata]
这些都是可以的,某些情况下,比较方便。
其中[bx+si]与[bx+di] 可以写成 [bx][si],[bx][di]
[bx+si+idata],[bx+di+idata] 可以写成idata[bx][si],idata[bx][di]
例子:复制Welcome!
- assume cs:code,ds:data
- data segment
- db 'Welcome! '
- data ends
- code segment
- start: mov ax,data
- mov ds,ax
- mov si,0
- mov cx,4
- s: mov ax,[si]
- mov 8[si],ax
- add si,2
- loop s
- mov ax,4c00H
- int 21H
- code ends
- end start
例子:将data中的单词的首字母改成大写
- assume cs:code,ds:data
- data segment
- db '1.file '
- db '2.edit '
- db '3.search'
- db '4.view '
- data ends
- code segment
- start: mov ax,data
- mov ds,ax
- mov bx,0
- mov cx,4
- mov al,11011111b
- s: and [bx+2],al
- add bx,8
- loop s
- mov ax,4c00H
- int 21H
- code ends
- end start
3. 双重循环
例子:data中单词改成大写的
- assume cs:code,ds:data
- data segment
- db 'ibm '
- db 'dec '
- db 'dos '
- db 'vax '
- data ends
- code segment
- start: mov ax,data
- mov ds,ax
- mov bx,0
- mov al,11011111b
- mov cx,4
- s: mov cx,3
- mov si,0
- s0: and [bx+si],al
- inc si
- loop s0
- add bx,8
- loop s
- mov ax,4c00H
- int 21H
- code ends
- end start
上面 的代码,是错误的会出现是死循环。因为cx不断的被赋予3,导致外层循环死循环。
- assume cs:code,ds:data
- data segment
- db 'ibm '
- db 'dec '
- db 'dos '
- db 'vax '
- data ends
- code segment
- start: mov ax,data
- mov ds,ax
- mov bx,0
- mov al,11011111b
- mov cx,4
- s: mov dx,cx ;dx用来临时存放外层的cx的值
- mov cx,3
- mov si,0
- s0: and [bx+si],al
- inc si
- loop s0
- mov cx,dx ;用来回复外层循环的cx
- add bx,8
- loop s
- mov ax,4c00H
- int 21H
- code ends
- end start
上面的代码,虽然能解决上面问题,能正常运行。但是寄存器的数量有限,有时,可能没有其他的寄存器可以用。
解决方法,保存在内存中。例子:
- assume cs:code,ds:data
- data segment
- db 'ibm '
- db 'dec '
- db 'dos '
- db 'vax '
- dw 0 ;定义一个字,用来保存cx
- data ends
- code segment
- start: mov ax,data
- mov ds,ax
- mov bx,0
- mov al,11011111b
- mov cx,4
- s: mov ds:[20H],cx
- mov cx,3
- mov si,0
- s0: and [bx+si],al
- inc si
- loop s0
- mov cx,ds:[20H]
- add bx,8
- loop s
- mov ax,4c00H
- int 21H
- code ends
- end start
上面的代码,解决了寄存器不够的情况。但是,还是比较复杂,如果有很多循环,就会弄不清楚。
解决方法,使用栈来保存恢复cx。例子1:
- assume cs:code,ds:data,ss:stack
- data segment
- db 'ibm '
- db 'dec '
- db 'dos '
- db 'vax '
- data ends
- stack segment
- dw 0,0,0,0,0,0,0,0
- stack ends
- code segment
- start: mov ax,data
- mov ds,ax
- mov ax,stack
- mov ss,ax
- mov sp,16
- mov bx,0
- mov al,11011111b
- mov cx,4
- s: push cx
- mov cx,3
- mov si,0
- s0: and [bx+si],al
- inc si
- loop s0
- pop cx
- add bx,8
- loop s
- mov ax,4c00H
- int 21H
- code ends
- end start
例子2:把data中的单词,前3个字母改成大写
- assume cs:code,ds:data,ss:stack
- data segment
- db '1.display.......'
- db '2.brows.........'
- db '3.replace.......'
- db '4.modify........'
- data ends
- stack segment
- dw 0,0,0,0,0,0,0,0
- stack ends
- code segment
- start: mov ax,data
- mov ds,ax
- mov ax,stack
- mov ss,ax
- mov sp,16
- mov bx,0
- mov al,11011111b
- mov cx,4
- s: push cx
- mov si,0
- mov cx,3
- s0: and [bx+si+2],al
- inc si
- loop s0
- pop cx
- add bx,10H
- loop s
- mov ax,4c00H
- int 21H
- code ends
- end start
上一篇:汇编入门学习笔记 (七)—— dp,div,dup
下一篇:汇编入门学习笔记 (五)—— 包含多个段的程序
推荐阅读最新更新时间:2024-03-16 14:58