加载中…
个人资料
  • 博客等级:
  • 博客积分:
  • 博客访问:
  • 关注人气:
  • 获赠金笔:0支
  • 赠出金笔:0支
  • 荣誉徽章:
正文 字体大小:

汇编语言(王爽 第三版)实验11 编写子程序

(2017-04-10 15:09:26)
标签:

汇编

王爽

it

教育

分类: 汇编语言(王爽第三版)实验

实验11  编写子程序

    编写一个子程序,将包含任意字符,以0结尾的字符串中的小写字母转变成大写字母,描述如下。

名称:letterc

功能:将以0结尾的字符串中的小写字母转变成大写字母

参数:ds:si指向字符串首地址

应用举例:

assume cs:codesg

datasg segment 

    db "Beginner's All-purpose Symbolic Instruction Code.",0 

datasg ends

codesg segment

begin:  mov ax, datasg

        mov ds, ax

        mov si, 0

       

        call letterc

       

        mov ax, 4c00H

        int 21H

letterc:    ????????

            ????????

codesg ends

end begin

程序分析:

1.在数据段定义了一个字符串,注意这个字符串不光是有大小写字符,还有其他字符,并以0结尾。(在C语言中字符串的存储也是按照0字符来结尾的,以前我们介绍了,这个是方便判断字符串是否到结尾处。)

老样子,在子程序中,首先将子程序预计使用到的变量入栈保存。axsi吧。

2.判断是否是结尾?也就是遇到0.

3. 判断字符串中的字符是否是小写字母?因为小写字母‘a~z’是连续的ASCII

4.如果是小写字母使用and指令转换成大写的。

5.这个子程序只是将该字符串的小写字母转换成了大写字母,但是调用它后没有任何的显示结果的,因为它只是个单纯的转换。

6.怎样测试结果?我们原来应该设计过显示字符串的子程序,可以使用把它显示在屏幕上;也可以使用debug来查看。这需要修改下这个子程序。

汇编代码如下:

assume cs:codesg

datasg segment 

    db "Beginner's All-purpose Symbolic Instruction Code.",0 ;注意0结尾

datasg ends

codesg segment

begin:  mov ax, datasg

        mov ds, ax          ;初始化ds

        mov si, 0           ;dssi指向字符串的首地址

        call letterc        ;调用子程序

        mov ax, 4c00H

        int 21H

letterc:    push ax

            push si         ;保存寄存器变量的值

       

    comp:   mov al, [si]    ;将字符读入al

            cmp al, 0       ;检测字符是否为0,字符串结尾检测

            je exit         ;如果为0,跳转到exit标号,退出

            cmp al, 'a'     ;与小写字母a比较

            jb next_char    ;如果小于字符a,跳转到下个字符

           

            cmp al, 'z'     ;与小写字母z比较

            ja next_char    ;如果大于字符z,跳转到下个字符

           

            and al, 11011111B   ;条件都不满足,开始转换为大写字母

           

    next_char:                  ;下一个字符,递增si,跳转到comp标号

            inc si

            jmp short comp

           

    exit:   pop si

            pop ax      ;

            ret

codesg ends

end begin

注:这个程序是不能测试结果的。

    为了测试结果,在原来代码基础上增加了将结果写入到字符串后面的内存单元中,并使用debug查看。

修改后的代码如下(红色的是新增代码):

assume cs:codesg

datasg segment 

db "Beginner's All-purpose Symbolic Instruction Code.",0 ;注意0结尾

    db 50 dup (0)                ;在字符串结尾增加50字节的空间,并初始化为0

datasg ends

codesg segment

begin:  mov ax, datasg

        mov ds, ax          ;初始化ds

        mov si, 0           ;dssi指向字符串的首地址

        mov di, 50          ;dsdi指向结果检测字符串的首地址

 

        call letterc        ;调用子程序

       

        mov ax, 4c00H

        int 21H

letterc:    push ax

            push si         ;保存寄存器变量的值

            push di         ;新增  

    comp:   mov al, [si]    ;将字符读入al

            cmp al, 0       ;检测字符是否为0,字符串结尾检测

            je exit         ;如果为0,跳转到exit标号,退出

            cmp al, 'a'     ;与小写字母a比较

            jb next_char    ;如果小于字符a,跳转到下个字符

           

            cmp al, 'z'     ;与小写字母z比较

            ja next_char    ;如果大于字符z,跳转到下个字符

           

            and al, 11011111B   ;条件都不满足,开始转换为大写字母

           

    next_char:                  ;下一个字符,递增si,跳转到comp标号

            mov [di], al        ;将转换后字符写入到结果内存单元中。

            inc di              ;新增

            inc si

            jmp short comp

           

    exit:   pop di      ;新增

            pop si

            pop ax      ;恢复寄存器变量值

            ret

           

codesg ends

end begin

编译并连接后,在debug中的实验结果如下:

-d ds:0

0B66:0000  42 65 67 69 6E 6E 65 72-27 73 20 41 6C 6C 2D 70   Beginner's All-p

0B66:0010  75 72 70 6F 73 65 20 53-79 6D 62 6F 6C 69 63 20   urpose Symbolic

0B66:0020  49 6E 73 74 72 75 63 74-69 6F 6E 20 43 6F 64 65   Instruction Code

0B66:0030  2E 00 42 45 47 49 4E 4E-45 52 27 53 20 41 4C 4C   ..BEGINNER'S ALL

0B66:0040  2D 50 55 52 50 4F 53 45-20 53 59 4D 42 4F 4C 49   -PURPOSE SYMBOLI

0B66:0050  43 20 49 4E 53 54 52 55-43 54 49 4F 4E 20 43 4F   C INSTRUCTION CO

0B66:0060  44 45 2E 00 00 00 00 00-00 00 00 00 00 00 00 00   DE..............

注意红色标注的是字符串的“.”和“0

0

阅读 收藏 喜欢 打印举报/Report
  

新浪BLOG意见反馈留言板 欢迎批评指正

新浪简介 | About Sina | 广告服务 | 联系我们 | 招聘信息 | 网站律师 | SINA English | 产品答疑

新浪公司 版权所有