汇编语言课程设计---统计数

统计数

1. 需求说明

 1.1设计要求:

进一步理解和掌握较复杂程序的设计方法,掌握子程序结构的设计和友好用户界面的设计。

具体的设计任务及要求:

1. 输入若干个十进制数据;

2. 统计其中最高6位全为1的数的个数;

3. 输出满足要求的数的个数和具体的数

4. 程序采用子程序结构或宏指令,结构清晰;

5.友好清晰的用户界面,能识别输入错误并控制错误的修改。

 1.2设计说明

     本程序首先需要输入一个0到9的数字并将其保存到cx中,用来确定需要输入数字的数量,首先,每次输入一个数字后就将它转化为10进制数字保存到buf中,将所有需要输入的数字输入完后再依次对buf中的数字进行判断,我的判断方法是利用循环将数字左移一位,判断cf的值来确定是否符合要求,最后将符合要求的数和个数输出,在进行判断是否再一次执行程序

 1.3功能简述

    程序可以首先输入一个小于10的数字n,确定要输入多少个数字,然后每输入一个数字检查是否超过1个字的存储范围;若输入有误则提示错误,并提示重新输入,若输入正确个字数据后,系统将显示出所有满足要求的数的个数和数。

    然后提示是否继续,若用户输入y或Y,则系统回到最开始的状态,若输入n或N,则退出系统,若为其他则提示错误,并重新输入。

2. 设计说明(简要的分析与概要设计)

 2.1简要分析

    2.1.1原理说明

本程序首先需要输入一个0到9的数字并将其保存到cx中,用来确定需要输入数字的数量,首先,每次输入一个数字后就将它转化为10进制数字保存到buf中,将所有需要输入的数字输入完后再依次对buf中的数字进行判断,我的判断方法是利用循环将数字左移一位,判断cf的值来确定是否符合要求,最后将符合要求的数和个数输出,在进行判断是否再一次执行程序

  2.1.2程序流程图

                                                                (主要操作流程图)

 

                                                        (将字符串转化成10进制)

 

                                                                 (将10进制数据输出)

2.2 数据段设计

data segment
	many db 'How many numbers you want to input(0~9)? $'
	tip db 'Please input a number(0~65535): $'
	next db 'Do you want to go on Y/N ?$'
	nice db 'The numbers you want are: $'
	fail db 'There is something wrong in your input! $'
	toll db ' numbers you want.$'
	nextword db ?
	buf dw 10 dup(0);设置buf区域保存转换后的数字
	string db 10;设置字符串输入区域
		   db 0
		   db 10 dup(0)				
	claf db 0dh,0ah,'$'
data ends

分析:

前六条语句主要用于进行提示性语句的输出

Nextword 变量用于保存所需输入字的个数

Buf 用于保存将字符串转化成10进制的数字

String 用于设计10号中断的字符串输入

Claf 用于换行的操作

3.主要子程序(或宏指令)设计与描述

1)clafp子程序

;----------
;子程序功能:换行
;使用到的寄存器:
;dx:保存偏移地址
;ah:调用中断
;------------
clafp proc
	lea dx,claf
	mov ah,9
	int 21h
	ret
clafp endp
;------------

2)cin子程序

;------------
;子程序功能:输入字符串
;使用到的寄存器
;cx:记录输入字的数量
;ah:调用中断
;dx:保存偏移地址
;------------------
cin proc
		dec cx
		lea dx,tip;输出提示性字符串
		mov ah,9
		int 21h
		call clafp
		mov ah,10
		lea dx,string;输入字符串
		int 21h
		push cx
		call tonum;将字符串转化成10进制数
		cmp al,1;判断是否满足要求
		jz L4
		pop cx
		inc cx
		push cx
L4:     pop cx
		call clafp
		ret
cin endp
;-----------------------

3)tonum子程序

;子程序功能:将字符串转化成10进制数
;用到的寄存器:si源字符串
;di指向目标地址
;cx保存字符串长度
;ax保存转换的字符
;bl保存每一位的字符
;----------------------------		
tonum proc 
	mov si,2
	mov cl,string+1;判断字数是否超出范围
	cmp cl,5
	ja err
	mov ch,0
	xor ax,ax
L2: 
	mov bl,string[si]
	inc si
	cmp bl,'9';判断每一位是否符合要求
	ja err
	cmp bl,'0'
	jb err
	sub bl,'0'
	mov bh,0
	mov dx,10;乘以10在加个位数
	mul dx
	jc err
	add ax,bx
	jc err
	loop L2
	mov buf[di],ax
	add di,2
	mov al,1
	ret
err:;如果错误则输出错误信息
	lea dx,fail
	mov ah,9
	int 21h
	lea dx,claf
	int 21h
	mov al,0
	ret
	tonum endp
;-----------------------

4)print子程序

;子程序功能:将字型数字输出
;用到的寄存器:
;si源字,在子程序前应该赋值
;ax,dx用于除法
;bx用作除数
;---------------------
print proc
	
	mov ax,buf[di]
	mov dx,0
	mov bx,10000;将10进制的每一位输出
	div bx;这里时间紧不做化简
	push dx
	mov dl,36h
	mov ah,2
	int 21h
	pop ax
	mov dx,0
	mov bx,1000
	div bx
	push dx
	mov dl,al
	mov ah,2
	add dl,30h
	int 21h
	pop ax
	mov dx,0
	mov bx,100
	div bx
	push dx
	mov dl,al
	mov ah,2
	add dl,30h
	int 21h
	pop ax
	mov dx,0
	mov bx,10
	div bx
	push dx
	mov dl,al
	mov ah,2
	add dl,30h
	int 21h
	pop ax
	mov dx,0
	mov bx,1
	div bx
	mov dl,al
	mov ah,2
	add dl,30h
	int 21h
	lea dx,claf
	mov ah,9
	int 21h
	ret 
	print endp
;---------------

5)judge子程序

;子程序功能:判断十进制数是否满足前6位为1
;用到的寄存器
;bx:保存10进制数
;cx:保存1的个数
;返回参数:若满足要求al=1,否则al=0
;--------------------
judge proc
	mov bx,buf[di]
	mov cx,6
	mov al,1
L3:
	shl bx,1;左移6次,判断cf是否为1
	jnc no
	loop L3
	jmp yes
yes:
	ret
 no: 
	mov al,0
	ret
judge endp

4.源程序与执行结果

4.1源程序代码

.386
data segment use16
	many db 'How many numbers do you want?(0~9)? $'
	tip db 'Please input a number(0~65535): $'
	next db 'Do you want to go on (input Y or N )?$'
	nice db 'The numbers meet your requirements: $'
	fail db 'There is something wrong in your input! Try again! $'
	toll db ' numbers meet your requirements.$'
	nextword db ?
	buf dw 10 dup(0);设置buf区域保存转换后的数字
	string db 10;设置字符串输入区域
		   db 0
		   db 10 dup(0)				
	claf db 0dh,0ah,'$'
data ends
stack segment use16 stack
	db 200 dup(0)
stack ends
code segment use16
	assume cs:code,ss:stack,ds:data
srart:
		mov ax,data
		mov ds,ax
L8:		mov di,0
		mov ah,9
		lea dx,many;输入提示数字多少的提示语句
		int 21h
		call clafp
		mov ah,1
		lea dx,nextword
		int 21h
		mov ah,0
		sub al,30h
		mov cx,ax;将输入次数保存到cx
		call clafp
L1:		
		call cin;调用子程序输入字符串
		cmp cx,0
		jnz L1
		mov di,0
		mov cx,0
		lea dx,nice;输出提示性字符串
		int 21h
		call clafp
L6:		push cx
		call judge
		pop cx
		cmp al,0;判断是否满足要求
		jz L7
		inc cx 
		call print
L7:		add di,2
		cmp di,20;判断是否读取完毕
		jnz L6
		mov dx,cx
		add dl,30h
		mov ah,2
		int 21h
		lea dx,toll;输出符合要求的总数
		mov ah,9
		int 21h
		call clafp
L9:		lea dx,next
		int 21h
		lea dx,nextword
		mov ah,1
		int 21h
		call clafp
		cmp al,'Y';判断是否为Y 或者 y
		jz L8
		cmp al,'y'
		jz L8
		cmp al,'N'
		jz L5
		cmp al,'n'
		jz L5
		lea dx,fail
		mov ah,9
		int 21h
		call clafp
		jmp L9
L5:
		mov ah,4ch
		int 21h
;----------
;子程序功能:换行
;使用到的寄存器:
;dx:保存偏移地址
;ah:调用中断
;------------
clafp proc
	lea dx,claf
	mov ah,9
	int 21h
	ret
clafp endp
;------------
;子程序功能:输入字符串
;使用到的寄存器
;cx:记录输入字的数量
;ah:调用中断
;dx:保存偏移地址
;------------------
cin proc
		dec cx
		lea dx,tip;输出提示性字符串
		mov ah,9
		int 21h
		call clafp
		mov ah,10
		lea dx,string;输入字符串
		int 21h
		push cx
		call tonum;将字符串转化成10进制数
		cmp al,1;判断是否满足要求
		jz L4
		pop cx
		inc cx
		push cx
L4:     pop cx
		call clafp
		ret
cin endp
;-----------------------
;子程序功能:将字符串转化成10进制数
;用到的寄存器:si源字符串
;di指向目标地址
;cx保存字符串长度
;ax保存转换的字符
;bl保存每一位的字符
;----------------------------		
tonum proc 
	mov si,2
	mov cl,string+1;判断字数是否超出范围
	cmp cl,5
	ja err
	mov ch,0
	xor ax,ax
L2: 
	mov bl,string[si]
	inc si
	cmp bl,'9';判断每一位是否符合要求
	ja err
	cmp bl,'0'
	jb err
	sub bl,'0'
	mov bh,0
	mov dx,10;乘以10在加个位数
	mul dx
	jc err
	add ax,bx
	jc err
	loop L2
	mov buf[di],ax
	add di,2
	mov al,1
	ret
err:;如果错误则输出错误信息
	lea dx,fail
	mov ah,9
	int 21h
	lea dx,claf
	int 21h
	mov al,0
	ret
	tonum endp
;-----------------------
;子程序功能:将字型数字输出
;用到的寄存器:
;si源字,在子程序前应该赋值
;ax,dx用于除法
;bx用作除数
;---------------------
print proc
	
	mov ax,buf[di]
	mov dx,0
	mov bx,10000;将10进制的每一位输出
	div bx;这里时间紧不做化简
	push dx
	mov dl,36h
	mov ah,2
	int 21h
	pop ax
	mov dx,0
	mov bx,1000
	div bx
	push dx
	mov dl,al
	mov ah,2
	add dl,30h
	int 21h
	pop ax
	mov dx,0
	mov bx,100
	div bx
	push dx
	mov dl,al
	mov ah,2
	add dl,30h
	int 21h
	pop ax
	mov dx,0
	mov bx,10
	div bx
	push dx
	mov dl,al
	mov ah,2
	add dl,30h
	int 21h
	pop ax
	mov dx,0
	mov bx,1
	div bx
	mov dl,al
	mov ah,2
	add dl,30h
	int 21h
	lea dx,claf
	mov ah,9
	int 21h
	ret 
	print endp
;---------------
;子程序功能:判断十进制数是否满足前6位为1
;用到的寄存器
;bx:保存10进制数
;cx:保存1的个数
;返回参数:若满足要求al=1,否则al=0
;--------------------
judge proc
	mov bx,buf[di]
	mov cx,6
	mov al,1
L3:
	shl bx,1;左移6次,判断cf是否为1
	jnc no
	loop L3
	jmp yes
yes:
	ret
 no: 
	mov al,0
	ret
judge endp
code ends
end srart

4.2 测试

 4.2.1 测试用例

   输入数字:1

  • 错误输入

66666

  • 错误输入

2313h

  • 正确输入

65500

    是否继续:Y

输入数字:2

  • 错误输入

123456

  • 错误输入

8940.3

  • 正确输入

54321

  • 正确输入

65432

4.2.2 测试结果(运行截图)

 

 

 

 

5.参考资料

1)《80X86汇编语言程序设计(王元珍等)》

2)《汇编语言(王爽第3版)》

 

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值