1. 程式人生 > >王爽.彙編.第三版.課程設計1.答案

王爽.彙編.第三版.課程設計1.答案

日期:2017年7月3日
課程設計 1
任務:將實驗7中的Power idea公司的資料按照下圖所示的格式在螢幕上顯示出來
這裡寫圖片描述
版本:beta 0.1
1、有時間再排版吧。都是用的第10章之前的指令。沒有優化程式碼
2、設計思路,為了簡單使用的是實驗七的程式碼,在生成每一行table後,直接將table中的一行作為print函式的引數;對齊方式為每10個字元佔一個欄位
3、每個函式的設計思路,註釋裡面in表示輸入引數,out表示輸出引數。in_out表示輸入輸出。

assume cs:code,ds:data,es:table  

data segment          
    db '1975'
,'1976','1977','1978','1979','1980','1981','1982','1983' db '1984','1985','1986','1987','1988','1989','1990','1991','1992' db '1993','1994','1995' ;以上是21年的21個字串 dd 16,22,382,1356,2390,8000,16000,24486,50065,97479,140417,197514 dd 345980,590827,803530,1183000,1843000,2759000
,3753000,4649000,5937000 ;以上是21個表示年收入的字串 dw 3,7,9,13,28,38,130,220,476,778,1001,1442,2258,2793,4037,5635,8226 dw 11542,14430,45257,17800 ;以上是21個僱傭人數 data ends ;臨時緩衝區 doublewordtostring_stack segment db 10 dup(0) doublewordtostring_stack ends table segment db 21 dup('year summ ne ?? '
) table ends string segment db 47 dup(' '),0 string ends color segment db 01000010b,11000010b,01110001b color ends code segment start: ;-------------------------------- ; 一下將結構整合到table中 mov ax,data mov es,ax ; 資訊來源 mov ax,table mov ds,ax ; 資訊目的地 mov cx,21 mov si,0 ;年份的索引(0-21*4) mov di,0 ;收入 mov bp,0 ;人數 mov bx,0 ;結果索引 mov dx, 0 ; 列印的行數 computerincome: push cx push dx ;year mov al, es:[si] mov ds:[bx],al mov al,es:[si+1] mov ds:[bx+1],al mov al,es:[si+2] mov ds:[bx+2],al mov al,es:[si+3] mov ds:[bx+3],al ;income, ready for div, set ax = so low word mov ax,es:[di+84] mov ds:[bx+5], ax ;ready for div, set dx = so high word mov dx,es:[di+86] mov ds:[bx+7], dx ;ne,ready for div, set cx = ne mov cx,es:[bp+168] mov ds:[bx+0ah], cx ;avrage div cx mov ds:[bx+0dh],ax pop dx pop cx push dx call print pop dx inc dh add si, 4 add di, 4 add bp, 2 add bx, 010h loop computerincome mov ax, 4c00h int 21h ;------------------------------------------------ ; ds:bx為資料來源:按照實驗7的結構,21行,沒行16位元組,此處使用的就是那16位元組的資料 ; dx:dh=row,dl=col print: push si push cx push bx push es push ds push dx push di push bp ; 本行字串 mov ax, string mov es, ax mov si, 0 ;------------- ; year mov al , byte ptr ds:[bx] mov byte ptr es:[si], al mov al , byte ptr ds:[bx+1] mov byte ptr es:[si+1], al mov al , byte ptr ds:[bx+2] mov byte ptr es:[si+2], al mov al , byte ptr ds:[bx+3] mov byte ptr es:[si+3], al add si, 10 ; 對齊10個字元 ;---------------- ; all income push ds push bx mov ax, ds:[bx+5] ;收入低16位 mov dx, ds:[bx+7] ;收入高16位 mov bx, es mov ds, bx call doublewordtostring add si, 10 ; 對齊10個字元 pop bx pop ds ;---------------- ; 人數 push ds push bx push ax mov ax, ds:[bx+0ah] mov bx, es mov ds, bx call wordtostring pop ax pop bx pop ds add si, 10 ; 對齊10個字元 ;----------------- ; 平均收入 push ds push bx mov cx, ds:[bx+0ah] ; 人數 call divdw mov bx, es mov ds, bx call doublewordtostring pop bx pop ds ;------------ ; ret pop bp pop di pop dx pop ds pop es pop bx pop cx pop si ;----------------- ; 開始列印 push ax push ds push si push cx mov ax, string mov ds, ax mov si, 0 mov cl, 01000010b call writestring mov al, ' ' call clearstring pop cx pop si pop ds pop ax ret ;------------------------------------------------ ; doubleword 轉化為字串 ; ax,為16低位。 ; dx,為16高位 ;ds:si, in_out,字串輸出地址:eeeeeeeeerrorrr doublewordtostring: push bx push dx push cx push ax push es push si ;----------- ;先逆序將所有數字轉成的字元放入堆疊 mov bx, 0 doublewordtostring_switch: push cx mov cx, 10 call divdw ;將除10後的商 add cx, 30h push ax push ds mov ax, doublewordtostring_stack mov ds, ax mov ds:[bx],cx pop ds pop ax pop cx inc bx cmp ax, 0 jne doublewordtostring_switch cmp dx, 0 jne doublewordtostring_switch ;--------------------- ;從臨時堆疊取出 mov cx, doublewordtostring_stack mov es, cx ; bx為逆序的索引索引 mov cx, bx dec bx doublewordtostring_s: mov al, byte ptr es:[bx] mov byte ptr ds:[si], al dec bx inc si loop doublewordtostring_s ;--------- pop si pop es pop ax pop cx pop dx pop bx ret ;end doublewordtostring ;------------------------------------------- ; word轉字串 ;ax, in, number ;ds:si, in_out,字串輸出地址 wordtostring: push bx push dx push cx push ax push ss push sp ;先逆序將所有數字轉成的字元放入堆疊 mov bx, 0 wordtostring_switch: mov dx, 0 push bx mov bx, 10 div bx pop bx add dx, 30h push dx ;放入堆疊 inc bx mov cx, ax jcxz wordtostring_okswitch jmp wordtostring_switch wordtostring_okswitch: ;從堆疊取出 mov cx, bx mov bx, 0 wordtostring_s: pop ax mov byte ptr ds:[si+bx], al inc bx loop wordtostring_s pop sp pop ss pop ax pop cx pop dx pop bx ret ;-- end wordtostring ;---------------------------------------------- ; 沒有溢位的除法計算 ;引數: ; (ax)= dword的低16位 ; (dx)= dword的高16位 ; (cx)= 除數 ;輸出 ; (ax)= 結果的低16位 ; (dx)= 結果的高16位 ; (cx)= 結果的餘數 divdw: push es push bx push si ;save low word,ax push ax ; ax = H, dx = 0, cx = L mov ax, dx mov dx, 0 ; ax = H/N, dx = H%N div cx ; save H/N mov bx, ax ; dx is H%N, ax = low word同時作為下次除法的高位 pop ax div cx ; ax=[rem(H/N)*65536+l]/N, dx = [rem(H/N)*65536+l]%N ; save 餘數 mov cx, dx ; ax = dx+H/N mov dx, bx pop si pop bx pop es ret ;------------------------------------------------ ;------------------------------------------------ ; 下面的函式為向螢幕輸出字串 ;------------------------------------------------ ;------------------------------------------------ ;------------------------------------------------ ; 獲取指定index的顏色 ; bx,in, color index ; al,out,color getcolor: ;al儲存從顏色表中讀的顏色 push ds push bx mov ax, color mov ds, ax mov ah, 0 mov al, ds:[bx] pop bx pop ds ret ;-------------------------------------------------- ; 使用al清理字串 ;ds:si,in, string's start pos ;al, string's defalt value clearstring: push ds push si push bx push cx mov bx, 0 mov cx, 0 clearstring_loop_set_0: mov cl, ds:[si+bx] jcxz clearstring_loop_ok mov ds:[si+bx], al inc bx jmp clearstring_loop_set_0 clearstring_loop_ok: pop cx pop bx pop si pop ds ret ;---------------------------------- ;cl,in, color ;dx,in,dh=row,dl=col ;ds:si,in, string's start pos writestring: push si push cx push bx push es push ds push dx ;視訊記憶體起始地址 mov bx, 0B800h mov es, bx ; ref pos call getpos mov bx, ax ;al=cl,save color mov al,cl putchar: mov ch,0 mov cl, ds:[si] ; 通過遇到字元0,跳出迴圈 jcxz okputchar ; 字元 mov byte ptr es:[bx], cl ; 顏色 mov byte ptr es:[bx+1], al inc si add bx, 2 jmp putchar okputchar: pop dx pop ds pop es pop bx pop cx pop si ret ;------------------------- ;dx,in,dh=row,dl=col ;ax,out,screen's ref pos ;ax = dh*160+dl getpos: push bx push dx ;8位乘法不會改變dx的值 mov bl, 160 mov al,dh mul bl mov dh, 0 add ax, dx pop dx pop bx ret code ends end start