汇编原理实验 --查找子字符串的位置

实验2:(子字符串,查找字符串在另一个字符串中出现的位置)

设计算法:将用户输入关键字和句子,将bx为关键字起始位置地址,dx赋初值为句子起始位置地址,将dx和bx内容进行匹配,如果不匹配则dx指向句子下一个字符及inc dx。用di表示当字符匹配成功时bx,dx的偏移量,di赋初值为0,[bx+di]与[dx+di]比较,如果匹配成功di自增1,直到di加到等于关键字长度时显示结果匹配成功,如果中间有匹配不成功di重置为0,直到当整个句子查询完没匹配则显示结果不匹配.

程序实现:调用print子程序,将缓冲区字符串显示出来,调用cin子程序将用户输入字符串存入指定缓冲区。另 cx=句子长度,用bx,dx分别等于关键字地址和句子地址按照前面所说的算法来编程。此外,还有一个要求需要显示当匹配成功时的子字符串位置:匹配的位置等于句子长度-cx,或匹配位置=dx-句子首地址,调用数字输出子程序。要注意的是:得出来的结果为十进制数字,要想以十六进制格式输出数字还需要将其转化成ASCII输出.

十六进制数字输出算法;(在附录中会附上十进制数输出代码)具体思路:将数字除以16,将余数压入栈中,商继续除以16,得出来的余数再压入栈中,

重复上述步骤,直到商为0时结束,再将栈顶元素依次推出并输出(判断是否小于10,小于10加30H输出,大于10加31h输出)。

DATAS SEGMENT
    ;此处输入数据段代码  
msg db 'enter keyword:$'
msg1 db 'enter sentence:$'
msg2 db 'NoMatch$'
msg3 db 'last Match location at:$'
keepcin db 100
cinlen	db 0
cinfld	db 100 dup(0)
keepcin1 db 100
cin1len	db 0
cin1fld		db 100 dup(0)
DATAS ENDS

STACKS SEGMENT
    ;此处输入堆栈段代码
STACKS ENDS

CODES SEGMENT
    ASSUME CS:CODES,DS:DATAS,SS:STACKS
START:
    MOV AX,DATAS
    MOV DS,AX
    mov es,ax
    ;此处输入代码段代码
    ;此处为标题输出和输入
    mov dx,offset msg
    call print   ;"enter keyword"    
    mov dx,offset keepcin
    call cin    
    mov dx,offset msg1
    call print    
    mov dx,offset keepcin1
    call cin
    
    ;用户输入完成接下来要完成字符串匹配
    mov bx,offset cinfld    ;关键字 
    mov dx,offset cin1fld   ;句子
    mov cl,cin1len          ;循环次数为句子长度
mat:
    call  comparestr		
    cmp al,0
    je match
    inc dx
    loop mat
    jmp noMatch		;遍历完都没找到
match:
	mov dx,offset msg3
    call print  
	mov al,cin1len
	sub al,cl
	mov dl,al 		;索引从0开始
	call dispdec
    jmp stop
noMatch:          ;没有查询到结果
    mov dx,offset msg2
    call print  
stop:   
	MOV AH,4CH
    INT 21H
 ;以下为子程序
comparestr proc    ;dx,bx指向字符串,比较字符串大小,相等为al=0,否则-1
 push cx
 push si
 push di
	mov si,dx
	mov di,bx ;
	mov cl,cinlen  ;改成字符串长度
	cld
lastagain: cmpsb
		   jnz lastunmat
		   loop lastagain
		   ;匹配成功
		   mov al,0
		   jmp lastoutput
lastunmat: mov al,-1
lastoutput:
pop di
pop si
pop cx
 ret
comparestr endp
;打印固定字符串
print proc
    push ax
    mov ah,09h
    int 21h
    pop ax
    ret
print endp
;十进制输出,入口参数dx
dispdec proc
		push ax
		push bx
		push cx
		push dx
        mov ax,dx
        xor dx,dx
        mov bx,10
        mov cx,0
a:
        cmp ax,10
        jb ok
        div bx
        add dl,30h
        push dx
        xor dx,dx
        inc cx
        jmp a
ok:
        add al,30h
        push ax
        inc cx
b:
        pop dx
        mov ah,2
        int 21h
        loop b
        pop dx
        pop cx
        pop bx
        pop ax
        ret
dispdec endp

;用户输入
cin proc
	 push ax
    mov ah,0AH
    int 21h
    pop ax
    call printnewline
    ret
cin endp
;输出换行
printnewline proc
	push ax
	push dx
	mov ah,02h
	mov dl,0dh
	int 21h
	mov dl,0ah
	int 21h
	pop dx
	pop ax
	ret
printnewline endp
CODES ENDS
    END START

输出结果如图:


  • 1
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值