汇编学习总结

                                                           汇编学习总结

因快期末考啦。。。下面是我个人对汇编学习的复习 大家可以忽略。。。。。。

        汇编大多是指汇编语言汇编程序。把汇编语言翻译机器语言的过程称为汇编。在汇编语言中,用助记符(Memoni)代替操作码,用地址符号(Symbol)或标号(Label)代替地址码。这样用符号代替机器语言的二进制码,就把机器语言变成了汇编语言。于是汇编语言亦称为符号语言。用汇编语言编写的程序,机器不能直接识别,要由一种程序将汇编语言翻译成机器语言,这种起翻译作用的程序叫汇编程序,汇编程序是系统软件中语言处理的系统软件。

        随着现代软件系统越来越庞大复杂,大量经过了封装的高级语言如C/C++,Pascal/Object Pascal也应运而生。这些新的语言使得程序员在开发过程中能够更简单,更有效率,使软件开发人员得以应付快速的软件开发的要求。而汇编语言由于其复杂性使得其适用领域逐步减小。但这并不意味着汇编已无用武之地。由于汇编更接近机器语言,能够直接对硬件进行操作,生成的程序与其他的语言相比具有更高的运行速度,占用更小的内存,因此在一些对于时效性要求很高的程序、许多大型程序的核心模块以及工业控制方面大量应用。

 

题目一:输入输出

键盘输入2个实数,然后按相反顺序输出这2个实数。
运行后若输入:3.3 4.45
则结果输出:4.45 3.3
运行后若输入:1.35 2.4
则结果输出:2.4 1.35

.386				;选择的处理器
.model flat, stdcall	
option casemap:none		;指明标识符大小写敏感
include	kernel32.inc	;要引用的头文件
includelib	kernel32.lib	;要引用的库文件
includelib	msvcrt.lib	;引用C库文件
scanf PROTO C:DWORD,:vararg	;C语言scanf函数原型声明
printf PROTO C:DWORD,:vararg;C语言printf函数原型声明
.data				;⑤数据段

 ;*【*/

a qword ?
b qword ?
fmt byte '%lf %lf',0
fmto byte '%g %g',0
.code
start:
invoke scanf,addr fmt,addr a,addr b
invoke printf,addr fmto,b,a

 ;*】*/

invoke	ExitProcess,0		;退出进程,返回值为0
end start

2、定义结构体商品,含编号、品名、单价、数量,输入一个商品信息求其金额并输出(按“%g”格式输出)。
若运行后输入:S001 小刀 4.5 2
则运行结果输出:编号:S001,品名:小刀,单价:4.5,数量:2,金额:9
请在;*【*/和;*】*/之间编写程序。
/***源程序asm***/

.386
.model flat, stdcall
option casemap :none
include kernel32.inc
includelib kernel32.lib
includelib	msvcrt.lib		;引用C库文件
printf PROTO C:ptr sbyte,:vararg	;C语言printf函数原型声明
scanf PROTO C:ptr sbyte,:vararg	;C语言scanf函数原型声明


 ;*【*/
.data
jin QWORD 9.0
fat BYTE '%s %s %lf %d',0;
outfat BYTE '编号:%s,品名:%s,单价:%g,数量:%d,金额:%g',0;
Show struct
id BYTE 14 DUP(?)
n BYTE 20 DUP(?)
dj QWORD 4.0
num DWORD 4
Show ends

s Show <>
.code
start:
invoke scanf,ADDR fat,ADDR s.id,ADDR s.n,ADDR s.dj,ADDR s.num;
FLD s.dj
FiMUL s.num
FSTP jin
invoke printf,ADDR outfat ,ADDR s.id,ADDR s.n,s.dj,s.num,jin;
invoke	ExitProcess,0		;退出进程,返回值为0
end start
 ;*】*/

 

题目二:加减乘除

1、输入两个小写字母,然后输出其相应的大写字母。
运行后输入:
a b
则结果输出:
A B
请在;*【*/和;*】*/之间编写程序。

.386				;选择的处理器
.model flat, stdcall	
option casemap:none		;指明标识符大小写敏感
include	kernel32.inc	;要引用的头文件
includelib	kernel32.lib	;要引用的库文件
includelib	msvcrt.lib	;引用C库文件
scanf PROTO C:DWORD,:vararg	;C语言scanf函数原型声明
printf PROTO C:DWORD,:vararg;C语言printf函数原型声明
.data				;⑤数据段
 ;*【*/
a BYTE ?
b BYTE ?
d BYTE ?
e BYTE ?

fmt BYTE '%c %c',0
fmto BYTE '%c %c',0
.code
start:
invoke scanf,ADDR fmt ,ADDR a,ADDR b;
MOV  EAX, DWORD PTR a
SUB EAX, 32
MOV  DWORD PTR d, EAX 

MOV  EAX, DWORD PTR b
SUB EAX, 32
MOV  DWORD PTR e, EAX 
invoke printf,ADDR fmto,DWORD PTR  d,DWORD PTR  e;

 ;*】*/
invoke	ExitProcess,0		;退出进程,返回值为0
end start

 

题目三:函数调用

1、键盘输入实数a和整数n的值,求a*2n的值:
运行后若输入:1.5 3
则结果输出:1.5*2^3=12
请在;*【*/和;*】*/之间编写程序。
/***源程序asm***/

 ;*【*/
.386
.model flat,stdcall
option casemap:none
include kernel32.inc
includelib kernel32.lib
includelib msvcrt.lib
scanf PROTO C:DWORD,:vararg
printf PROTO C:DWORD,:vararg
.data
a QWORD ?
n DWORD ?
z QWORD ?
fmt BYTE '%lf %d',0
fmt2 BYTE '%g*2^%d=%g',0
.code
start:
invoke scanf,ADDR fmt,ADDR a,ADDR n
FILD n
FLD a
FSCALE 
FSTP z

invoke printf,ADDR fmt2,a,n,z
invoke ExitProcess,0
end start

 ;*】*/

 

2、已知机器人当前的位置为(0,0),若该机器人的下一个位置为(x,y),请计算该机器人前进的方向角(角度)。输入x和y值,用反正切函数指令(FPATAN)求角度。
运行后若输入:1.0 1.0
则结果输出:45
运行后若输入:-1.0 1.0
则结果输出:135
运行后若输入:1.0 -1.0
则结果输出:-45
运行后若输入:-1.0 -1.0
则结果输出:-135
请在;*【*/和;*】*/之间编写程序。

 ;*【*/
.386
.model flat,stdcall
option casemap:none
include kernel32.inc
includelib kernel32.lib
includelib msvcrt.lib
scanf PROTO C:DWORD,:vararg
printf PROTO C:DWORD,:vararg
.data

x QWORD 180.0
y QWORD 3.1415926
a QWORD ?
b QWORD ?
z QWORD ?
s QWORD ?
d QWORD ?

fmt BYTE '%lf %lf',0
fmt2 BYTE '%g',0
.code
start:
invoke scanf,ADDR fmt,ADDR a,ADDR b
FLD b
FLD a
FPATAN
FSTP z

FLD z
FMUL x
FSTP s

FLD s
FDIV y
FSTP d


invoke printf,ADDR fmt2,d
invoke ExitProcess,0
end start


 ;*】*/

 

3、键盘输入实数a和整数n的值,求a*2n的值:
运行后若输入:1.5 3
则结果输出:1.5*2^3=12
请在;*【*/和;*】*/之间编写程序。
/***源程序asm***/

 ;*【*/
.386
.model flat,stdcall
option casemap:none
include kernel32.inc
includelib kernel32.lib
includelib msvcrt.lib
scanf PROTO C:DWORD,:vararg
printf PROTO C:DWORD,:vararg
.data
a QWORD ?
n DWORD ?
z QWORD ?
fmt BYTE '%lf %d',0
fmt2 BYTE '%g*2^%d=%g',0
.code
start:
invoke scanf,ADDR fmt,ADDR a,ADDR n
FILD n
FLD a
FSCALE 
FSTP z

invoke printf,ADDR fmt2,a,n,z
invoke ExitProcess,0
end start

 ;*】*/

 

题目四:选择结构

1、编写一段程序,完成下面计算公式,其中:变量x和y都是REAL8类型,结果保留2位小数。

运行后若输入:-2.0
则结果输出:-0.91
运行后若输入:0.52
则结果输出:1.04
运行后若输入:2.0
则结果输出:-0.42
请在;*【*/和;*】*/之间编写程序。
/***源程序asm***/

 ;*【*/

.386						;选择的处理器
.model flat, stdcall		;存储模型,Win32程序只能用平展(flat)模型
option casemap:none			;指明标识符大小写敏感
include	kernel32.inc		;要引用的头文件
includelib	kernel32.lib	;要引用的库文件
includelib	msvcrt.lib		;引用C库文件
scanf PROTO C:DWORD,:vararg	;C语言scanf函数原型声明
printf PROTO C:DWORD,:vararg	;C语言printf函数原型声明
.data						;⑤数据段
x QWORD ?
a QWORD -1.0
b QWORD 1.0
d QWORD 2.0
y QWORD ?
intfmt BYTE '%lf',0
outfmt BYTE '%.2lf',0
.code
start:
invoke scanf,addr intfmt,addr x
FEQU=40H
FLESS=1
FLD x
FCOMP a
fnstsw ax
.IF (AH&FLESS)
FLD x
FSIN
FSTP y
invoke printf,addr outfmt,y
.ELSE
FLD x
FCOMP b
fnstsw ax
.IF AH & (FLESS or FEQU)
FLD x
FMUL d
FSTP y
invoke printf,addr outfmt,y
.ELSE
FLD x
FCOS
FSTP y
invoke printf,addr outfmt,y
.ENDIF
.ENDIF
invoke ExitProcess,0		;⑨退出进程,返回值为0
end	start					;⑩指明程序入口点
 ;*】*/

 

 2、用.IF….ELSEIF伪指令实现输入一个分数(0~100的整数),输出相应的成绩等级。分数与成绩等级对应关系分别为90~100分为优秀,80~89为良好,70~79为中,60~69为及格,0~59为不及格。
运行后若输入:95
则结果输出:优秀
运行后若输入:86
则结果输出:良好
运行后若输入:73
则结果输出:中
运行后若输入:66
则结果输出:及格
运行后若输入:53
则结果输出:不及格
请在;*【*/和;*】*/之间编写程序。

.386						;选择的处理器
.model flat, stdcall		;存储模型,Win32程序只能用平展(flat)模型
option casemap:none			;指明标识符大小写敏感
include	kernel32.inc		;要引用的头文件
includelib	kernel32.lib	;要引用的库文件
includelib	msvcrt.lib		;引用C库文件
scanf PROTO C:DWORD,:vararg	;C语言scanf函数原型声明
printf PROTO C:DWORD,:vararg	;C语言printf函数原型声明
.data						;⑤数据段
 ;*【*/
x DWORD ?
s BYTE '优秀',0
s1 BYTE '良好',0
s2 BYTE '中',0
s3 BYTE '及格',0
s4 BYTE '不及格',0
fmt BYTE '%d',0
fmto BYTE '%s',0
.code
start:
invoke scanf,ADDR fmt,ADDR x;
.IF x>=90
invoke printf,ADDR fmto,ADDR s; 
.ELSEIF x>=80&&x<=89
invoke printf,ADDR fmto,ADDR s1; 
.ELSEIF x>=70&&x<=79
invoke printf,ADDR fmto,ADDR s2; 
.ELSEIF x>=60&&x<=69
invoke printf,ADDR fmto,ADDR s3; 
.ELSEIF x<60
invoke printf,ADDR fmto,ADDR s4; 
.ENDIF
 ;*】*/
invoke ExitProcess,0		;⑨退出进程,返回值为0
end	start					;⑩指明程序入口点start

 

题目五:循环结构

1、输入若干整数,统计正数与负数和。
运行后若输入:1 -2 3 -4
则结果输出:正数和为:4 负数和为:-6
请在;*【*/和;*】*/之间编写程序。
/***源程序asm***/

.386				;选择的处理器
.model flat, stdcall		;存储模型,Win32程序只能用平展(flat)模型
option casemap:none		;指明标识符大小写敏感
includelib	msvcrt.lib	;引用C库文件
scanf PROTO C:DWORD,:vararg	;C语言scanf函数原型声明
printf PROTO C:DWORD,:vararg	;C语言printf函数原型声明
.data				;⑤数据段
szFmt  	BYTE	'正数和为:%d 负数和为:%d',0
 ;*【*/
a sdword ?
Infmt byte '%d',0
.code
start:
            invoke scanf,addr Infmt,addr a
            mov esi,0
            mov edi,0
            .while eax==1
                    .if a>0
                            add esi,a
                    .else
                            add edi,a
                    .endif
                    invoke scanf,addr Infmt,addr a               
           .endw
          invoke printf,addr szFmt,esi,edi
ret
 ;*】*/
end start 

 

2、键盘输入若干对实数x、y,求各对实数乘积和。
运行后若输入:
2.5 2
1.5 4
2.2 2
则结果输出:
15.4
请在;*【*/和;*】*/之间编写程序。

 ;*【*/
.386
.model flat, stdcall
include kernel32.inc
includelib kernel32.lib
includelib	msvcrt.lib				;引用C库文件
printf PROTO C:ptr sbyte,:vararg	;C语言printf函数原型声明
scanf PROTO C:ptr sbyte,:vararg	;C语言scanf函数原型声明
option casemap :none 
.data
x qword ?
y qword ?
s qword 0.0
z qword ?
Infmt byte '%lf %lf',0
Outfmt byte '%g',0
.code
start:
       invoke scanf,addr Infmt,addr x,addr y
        fld s
          .while eax==2
           fld x 
           fmul y       
           fstp z
   
           
           fadd z 
          invoke scanf,addr Infmt,addr x,addr y
           
       .endw
        fstp s   
        invoke printf,addr Outfmt,s
invoke ExitProcess,0
end start
 ;*】*/

 

3、键盘输入一串字符(最多80个字符),输出其中的数字。
运行后若输入:ab4du5jkf8
则结果输出:458
请在;*【*/和;*】*/之间编写程序。
/***源程序asm***/

 ;*【*/
.386
.model flat, stdcall
include kernel32.inc
includelib kernel32.lib
includelib	msvcrt.lib				;引用C库文件
printf PROTO C:ptr sbyte,:vararg	;C语言printf函数原型声明
scanf PROTO C:ptr sbyte,:vararg	;C语言scanf函数原型声明
option casemap :none 
.data
s byte 80 dup(0)
Infmt byte '%s',0
Outfmt byte '%c',0
.code
start:
     invoke scanf,addr Infmt,addr s
     lea esi,s
     .while byte ptr[esi]!=0
           .if byte ptr[esi]>='0' && byte ptr[esi]<='9'
                   mov al,byte ptr[esi]
                   invoke printf,addr Outfmt,al
           .endif
           inc esi
     .endw


invoke ExitProcess,0
end start

 ;*】*/

 

题型六:c嵌入汇编

1、键盘输入a和b两串字符,编程实现将a串和b串连接的结果存入字符数组c[50]并输出。
如:
运行后输入:ABCD  abcd
则结果输出:ABCDabcd 


运行后输入:AB  a
则结果输出:ABa
请在/*【*/和/*】*/之间编写程序。
注意:不要删除或增加/*【*/和/*】*/。

#include "stdio.h"
#include "string.h"
void main()
{
char a[50]="ABCD",b[50]="abcd",c[50]={0};
int n,m;
scanf("%s %s",a,b);
n=strlen(a);m=strlen(b);
__asm
{
/*【*/
    cld
    lea esi,a
    lea edi,c
    mov ecx,n
    rep movsb
    
    lea esi,b
    lea edi,c
    add edi,n
    mov ecx,m
    rep movsb
/*】*/
}
printf("%s",c);
}

  

2、将字符数组a[63]中的数字删除(相当于把字母移到起始位置)。
注意:字符串结束标志也移。
如:
运行后输入:null(不输入)
则结果输出:ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz
请在/*【*/和/*】*/之间编写程序。
注意:不要删除或增加/*【*/和/*】*/。
/***源程序***/

#include "stdio.h"
void main()
{
char a[63]="0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
	__asm
	{
/*【*/
cld
lea esi,a+10
lea edi,a
mov ecx,53
rep movsb


/*】*/
	}
	printf("%s",a);
}

 

 题型七:子程序

1、编一串拷贝子程序,实现C语言char* strcpy(char *Dst,char *Src)函数,然后主程序调用strcpy(s1,s2)实现s2串拷贝到s1串。
运行后输入:
ABCD
则结果输出:
ABCD
请在;*【*/和;*】*/之间编写程序。
/***源程序asm***/

.386				;选择的处理器
.model flat, stdcall		;存储模型,Win32程序只能用平展(flat)模型
option casemap:none		;指明标识符大小写敏感
include	kernel32.inc		;要引用的头文件
includelib	kernel32.lib	;要引用的库文件
includelib	msvcrt.lib	;引用C库文件
scanf PROTO C:DWORD,:vararg	;C语言scanf函数原型声明
printf PROTO C:DWORD,:vararg	;C语言printf函数原型声明
.data				;⑤数据段
fmt	BYTE	'%s',0		;定义变量
s1	BYTE	80 Dup(0)
s2	BYTE	80 Dup(0)
.code				;⑥代码段
 ;*【*/
 strcpy proc,Str1:dword,Str2:dword
 mov esi,Str1
 mov edi,Str2
 .while byte ptr[esi]!=0
           inc esi
         
 .endw

 .while byte ptr[edi]!=0
         mov al,byte ptr[edi]
         mov byte ptr[esi],al
         inc esi
         inc edi
 .endw
 ret
 strcpy endp

 ;*】*/
start:				;定义标号start
invoke scanf,ADDR fmt,ADDR s2	;输入s2的值
invoke strcpy,ADDR s1,ADDR s2	;求s2串拷贝到s1串
invoke printf,ADDR fmt,ADDR s1	;输出
invoke ExitProcess,0		;退出进程,返回值为0
end	start			;指明程序入口点start

 

2、编一函数MaxN(int a[],int n)用于求n个元素的数组a中的最大元素。
运行后输入:
1 3 4 5 2
则结果输出:
最大值为5
运行后输入:
1 3 6 4 5 2
则结果输出:
最大值为6
请在;*【*/和;*】*/之间编写程序。
/***源程序asm***/
 

.386				;选择的处理器
.model flat, stdcall		;存储模型,Win32程序只能用平展(flat)模型
option casemap:none		;指明标识符大小写敏感
include	kernel32.inc		;要引用的头文件
includelib	kernel32.lib	;要引用的库文件
includelib	msvcrt.lib	;引用C库文件
scanf PROTO C:DWORD,:vararg	;C语言scanf函数原型声明
printf PROTO C:DWORD,:vararg	;C语言printf函数原型声明
.data				;⑤数据段
Infmt	BYTE	'%d',0
Outfmt	BYTE	'最大值为%d',0
a		DWORD	80 Dup(0) 	;定义数组a
.code				;⑥代码段
 ;*【*/
MaxN proc,s:dword,i:dword
mov esi,0
mov ebx,s
mov eax,[ebx+esi*4]
.while esi<i
      .if [ebx+esi*4]>eax
             mov al,[ebx+esi*4]
      .endif
       inc esi
.endw
ret
MaxN endp

 ;*】*/
start:				;定义标号start
mov		ESI,0
invoke scanf,ADDR Infmt,ADDR a[ESI*4];输入a[i]的值
.while	EAX==1
INC		ESI
invoke scanf,ADDR Infmt,ADDR a[ESI*4];
.endw
invoke MaxN,ADDR a,ESI		;求a数组和通过EAX返回
invoke printf,ADDR Outfmt,EAX;输出结果
invoke ExitProcess,0		;退出进程,返回值为0
end	start			;指明程序入口点start

 

  • 3
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

代码敌敌畏

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值