;**********************電話號碼表實現*******************************
;在本次試驗中需要注意基址寄存器BX的移動方法,對以字為單位的數組,BX的移動方式
;是每移動一次加2或者減2
;另外函數調用的過程中需要小心PUSH和pop的調用是否安全,例如在name_sort中pop CX的
;時候沒有先Push CX,導致了name_sort函數不可以調用
;此程序使用比較高效的方法只是對號碼單的首地址進行排序,為此開辟了一個地址數組
;AdTable,類似C語言中的指針數組
;在每個名字的前面存有每個名字的長度,有利于對名字進行比較,體現了空間換時間
;程序調試難度較大,費時2天長度,長度349行
;12月7日于海韻
;==================================================================
DateArea segment
TemplateName db 20,?,20 dup(?)
TemplateNumber db 9,?,9 dup(?)
PhoneTable db 50 dup ( 21 dup (?), 8 dup (?) ,'$')
AdTable dw 50 dup (?)
FindedAdress dw 1 dup (?)
InputNamePrint db 13,10,'Input name:','$'
InputNumPrint db 13,10,'Input a telephone number:','$'
AskForNumPrint db 13,10,'Do you want a telepment numbre:(Y/N)','$'
NamePrint db 13,10,'name?','$'
AnswerFindedPrint db 13,10,'name',16 dup (20h),'tel.',13,10,'$'
AnswerNoFindPrint db 13,10,'NO SUCH NAME!','$'
DateArea ends
;=====================================================================
CodeArea segment
assume cs:CodeArea ,ds:DateArea ,es:DateArea
;-----------------------------
main proc far
push ds
sub ax,ax
push ax
mov ax,DateArea
mov ds,ax
mov es,ax
;
mov bx,0
lea si,PhoneTable
Start:
lea dx , InputNamePrint
mov ah,09h
int 21h
;
lea di,AdTable
mov AdTable[bx],si
call input_name;該函數還要返回輸入字母為終止時候的提示,
;可以返回一個寄存器的狀態來表示
jz Search
call stor_name
;
lea dx, InputNumPrint
mov ah ,09h
int 21h
;
call inphone
;
add si,30
add bx ,2
jmp Start
Search:
;lea dx, AskForNumPrint
;mov ah,09h
;int 21h
call name_sort
lea dx, AskForNumPrint
mov ah,09h
int 21h
;
mov ah,1
int 21h
sub al,4Eh
;
jz Exit
;
lea dx,NamePrint
mov ah,09h
int 21h
;
call input_name
;
call name_search
;
call printline
;
jmp Search
Exit: ret
main endp
;------------------------------
input_name proc near
push ax
push bx
push cx
push dx
push si
push di
;
lea dx,TemplateName
mov ah,0ah
int 21h
lea di ,TemplateName
add di,1
mov al,[di]
cmp al,0
;
pop di
pop si
pop dx
pop cx
pop bx
pop ax
;
ret
input_name endp
;------------------------------
stor_name proc near
push ax
push bx
push cx
push dx
push si
push di
;
mov di,AdTable[bx]
lea si,TemplateName
add si,1
mov dx,21
mov cl,[si]
mov al,cl
cbw
mov cx,ax
inc cx
sub dx,cx
cld
repnz movsb
mov cx,dx
cld
mov al ,20h
repnz stosb
;
pop di
pop si
pop dx
pop cx
pop bx
pop ax
;
ret
;
stor_name endp
;------------------------------
inphone proc near
push ax
push bx
push cx
push dx
push si
push di
;
lea dx,TemplateNumber
mov ah,0ah
int 21h
;
mov di,AdTable[bx]
add di,21
lea si,TemplateNumber
add si,1
mov cl,[si]
mov al,cl
cbw
mov cx,ax
add si,1
cld
repnz movsb
;
pop di
pop si
pop dx
pop cx
pop bx
pop ax
;
ret
inphone endp
;------------------------------
name_sort proc near
push ax
push bx
push cx
push dx
push si
push di
lea dx, AskForNumPrint
mov ah,09h
int 21h
mov cx,bx
OuterSort:
mov bx,0
InnerSort:
mov si,AdTable[bx]
add bx,2
mov di ,AdTable[bx]
mov al,[si]
mov dl,[di]
cmp al,dl
push cx
jg AxGrBx
mov al,dl
cbw
mov cx,ax
jmp PassAGB
AxGrBx:
cbw
mov cx,ax
PassAGB:
add si ,1
add di ,1
cld
repz cmpsb
pop cx
jb Belower
mov ax,AdTable[bx]
sub bx,2
mov dx,AdTable[bx]
xchg ax,dx
mov AdTable[bx],dx
add bx,2
mov AdTable[bx],ax
Belower:
mov ax,bx
add ax,2
cmp ax,cx
jnz InnerSort
sub cx,2
cmp cx,2
jnz OuterSort
pop di
pop si
pop dx
pop cx
pop bx
pop ax
ret
name_sort endp
;------------------------------
name_search proc near
push ax
push bx
push cx
push dx
push si
push di
mov ax,bx
mov bx ,0
mLoop:
lea si,TemplateName+1
mov cl,[si]
push ax
mov al,cl
cbw
mov cx,ax
add cx,1
pop ax
mov di,AdTable[bx]
cld
repz cmpsb
jz FindOutNum
add bx, 2
cmp bx ,ax
jz FindNoNum
jmp mLoop
FindNoNum:
pop di
pop si
pop dx
pop cx
pop bx
pop ax
ret
FindOutNum:
mov dx,AdTable[bx]
add dx,1
mov FindedAdress,dx
;mov ah,09h
; int 21h
pop di
pop si
pop dx
pop cx
pop bx
pop ax
ret
name_search endp
;------------------------------
printline proc near
push ax
push bx
push cx
push dx
push si
push di
jz NoFind
lea dx,AnswerFindedPrint
mov ah,09
int 21h
mov dx,[FindedAdress]
mov ah,09h
int 21h
JMP RetPlace
NoFind:
lea dx,AnswerNoFindPrint
mov ah,09h
int 21h
RetPlace:
pop di
pop si
pop dx
pop cx
pop bx
pop ax
ret
printline endp
;------------------------------
CodeArea ends
end main