汇编实验4(99乘法表,整数分解,素数环,迷宫问题)【栈传参,递归,寻址方式】

简介: 汇编实验4(99乘法表,整数分解,素数环,迷宫问题)【栈传参,递归,寻址方式】

一、99乘法表

汇编代码

1. INCLUDE Irvine32.inc
2. .data
3. a db '*',0
4. .code
5. main PROC
6. mov ebx,1;ebx=i
7. mov ecx,1;ecx=j
8. l0:
9. cmp ebx,9
10. ja final
11. mov ecx,1
12. l2:
13. cmp ecx,ebx
14. ja l1
15. mov eax,ebx
16. call writedec
17. mov al,a
18. call writechar
19. mov eax,ecx
20. call writedec
21. mov al,' '
22. call writechar
23. call writechar
24. inc ecx
25. jmp l2
26. l1:
27. call crlf
28. inc ebx
29. jmp l0
30. final:
31.    exit
32. main ENDP
33. end main
34. 
35. #include <stdio.h>
36. int main(){
37.     int i,j;
38. for(i=1;i<=9;i++)
39.     {
40. for(j=1;j<=i;j++)
41.             {printf("%d*%d=%2d  ",i,j,i*j);}
42.         printf("\n");
43.     }
44. 
45. return 0;
46. }

效果

貌似有点问题,忘了把运算结果加上......

二、整数拆分

问题描述

问题描述

输入一个N,输出所有拆分的方式。

如input: 3

output:

1+1+1

1+2

3

算法思想

用一个数组res[]存放拆分的解,用全局变量存放拆分的方法数。

divN(n,k)使用n表示要分解的整数,k表示res数组下标,即第k次拆分。

先从divN(n,1)开始,用num表示第k个拆分的数,即res[k]=num,

让num在[1,n]内遍历。用rest=n-num表示拆分后剩下的整数值。若rest等于零,

代表本次拆分结束,输出拆分解。否则处理第k+1个数组元素,即divN(rest,k+1),

依次类推,直到rest为0输出结果。

c代码

1. #include "stdafx.h"
2. #include<stdio.h>
3. #include<stdlib.h>
4. int res[10000] = { 0 }; //res数组存放解
5. int times = 0; //times计算拆分的次数
6. void divN(int n, int k) { //n是需要拆分的整数,k是指res数组的下标
7. int rest; //存放拆分后剩余的整数
8. for (int num = 1;num <= n; num++) {  //从1开始尝试拆分
9. if (num >= res[k - 1] ) { //拆分的解要大于或等于前一个解保证不重复
10.             res[k] = num; //将这次拆分存放在res数组中
11.             rest = n - num; //剩下的是n-num
12. if (rest == 0) { //如果没有剩下的,说明本次拆分结束
13.                 times++;  //拆分次数加1
14.     printf("%3d:", times);
15. for (int j = 1; j < k; j++) {  //输出解
16. printf("%d+", res[j]);
17.                 }
18. printf("%d\n", res[k]);
19.             }
20. else divN(rest, k + 1);  //如果有剩下的,继续求出res[k+1]
21.         }
22.     }
23. }
24. int main() {
25. int n;
26. printf("Please enter a integer N:");
27. scanf_s("%d", &n);
28. divN(n, 1);
29. printf("there are %d ways to divide the integer %d.", times,n);
30. system("pause");
31. return 0;
32. }

汇编代码

1. INCLUDE Irvine32.inc
2. .data
3. res dd 10000 dup(0)
4. times dd 0
5. n dd ?
6. st1 db 'Please enter a integer N:',0
7. .code
8. main PROC
9. mov edx,offset st1
10. call writestring
11. call readint
12. mov n,eax
13. push n
14. push 1
15. call divN
16. exit
17. main ENDP
18. 
19. divN PROC
20. push ebp
21. mov ebp,esp
22. pushad
23. mov ecx,[ebp+8];ecx=k
24. mov edx,[ebp+12];edx=n
25.                ;edi=rest
26. mov ebx,1;ebx=num
27. l0:;for
28. cmp ebx,edx
29. ja final
30. mov eax,ebx;eax=ebx
31. cmp eax,res[4*ecx-4]
32. jl l1
33. mov res[4*ecx],eax
34. mov eax,edx
35. sub eax,ebx;eax=n-ebx
36. mov edi,eax
37. cmp edi,0
38. jnz l2
39. inc times
40. mov eax,times
41. call writedec
42. mov al,' '
43. call writechar
44. mov esi,1;esi=j
45. l3:;for
46. cmp esi,ecx
47. jae l4
48. mov eax,res[+4*esi]
49. call writedec
50. mov al,'+'
51. call writechar
52. inc esi
53. jmp l3
54. l4:
55. mov eax,res[4*ecx]
56. call writedec
57. call crlf
58. jmp l1
59. l2:;else
60. push edi
61. mov eax,ecx
62. inc eax;eax=k+1
63. push eax
64. call divN
65. l1:
66. inc ebx
67. jmp l0
68. final:
69. popad
70. pop ebp
71. ret 8
72. divN ENDP
73. END main

效果

 

三、素数环

问题描述

素数环

题目:输入正整数n,把整数1,2,3,...,n组成一个环。

使得相邻两个整数之和均为素数。

输出时从整数1開始逆时针排列。

同一个环应该恰好输出一次。

c代码

1. #include<iostream>
2. #include<cstdio>
3. #include<cstring>
4. using namespace std;
5. 
6. const int maxn =1000;
7. int vis[maxn];
8. int A[maxn];
9. int isp[maxn];
10. int n;
11. int ans=0;
12. 
13. int is_prime(int x){
14. for( int i=2; i*i<=x; i++ ){
15. if(x%i==0) return 0;
16.     }
17. return 1;
18. }
19. 
20. void dfs(int cur){
21. if(cur==n&&isp[A[0]+A[n-1]]){
22.         ans++;
23. for( int i=0; i<n; i++ ) cout<<A[i]<<" ";
24.         cout<<endl;
25.     }
26. else{
27. for(int i=2; i<=n; i++ ){
28. if(!vis[i]&&isp[i+A[cur-1]]){
29.          /*i这个数没被用过,并且符合前后两个数相加为素数的要求*/
30.                 A[cur]=i;/*采用这个数*/
31.                 vis[i]=1;/*设置使用标志*/
32. dfs(cur+1);
33.                 vis[i]=0;/*消除标志*//*回溯的本质*/
34.             }
35.         }
36.     }
37. }
38. 
39. int main(int argc, char const *argv[])
40. {
41.     cin>>n;
42. memset(vis,0,sizeof(vis));
43. for( int i=2; i<=n*2; i++ ) isp[i]=is_prime(i);
44.     A[0]=1;/*题目中规定从1开始*/
45. dfs(1);
46.     cout<<ans<<endl;
47. 
48. return 0;
49. }

汇编代码

1. INCLUDE Irvine32.inc
2. .data
3. ans dd 0
4. vis dd 1000 dup(0)
5. A dd 1000 dup(?)
6. isp dd 1000 dup(?)
7. n dd ?
8. .code
9. main PROC
10. mov ecx,offset A
11. mov eax,1
12. mov [ecx],eax
13. mov eax,0
14. call readint
15. mov n,eax
16. mov ebx,2;ebx=i
17. l0:
18. mov eax,n
19. add eax,eax;eax=2*n
20. cmp ebx,eax
21. ja l1
22. push ebx
23. call is_prime
24. mov ecx,offset isp;ecx=isp
25. mov [ecx+4*ebx],eax
26. inc ebx
27. jmp l0
28. l1:
29. push 1
30. call dfs
31. mov eax,ans
32. call writedec
33. call crlf
34. exit
35. main ENDP
36. 
37. is_prime PROC
38. push ebp
39. mov ebp,esp
40. sub esp,4
41. pushad
42. mov ebx,[ebp+8];ebx=x
43. mov ecx,2;ecx=i
44. mov eax,0
45. mov [ebp-4],eax
46. l0:
47. mov eax,ecx
48. mul ecx
49. cmp eax,ebx
50. ja final1
51. mov edx,0
52. mov eax,ebx
53. div ecx
54. cmp edx,0
55. je final2
56. inc ecx
57. jmp l0
58. final1:
59. mov eax,1
60. mov [ebp-4],eax
61. final2:
62. popad
63. mov eax,[ebp-4]
64. add esp,4
65. pop ebp
66. ret 4
67. is_prime ENDP
68. 
69. dfs PROC
70. push ebp
71. mov ebp,esp
72. pushad
73. mov ebx,[ebp+8];ebx=cur
74. mov ecx,offset A;ecx=A
75. mov esi,offset isp;esi=isp
76. mov edi,offset vis;edi=vis
77. cmp ebx,n
78. jne l0
79. mov eax,[ecx]
80. mov esi,n
81. add eax,[ecx+esi*4-4];eax=A[0]+A[n-1]
82. mov esi,offset isp;esi=isp
83. mov eax,[esi+eax*4];eax=isp[A[0]+A[n-1]]
84. cmp eax,1
85. jne l0
86. inc ans
87. mov edx,0;edx=i
88. l1:
89. cmp edx,n
90. jae l2
91. mov eax,[ecx+edx*4]
92. call writedec
93. mov al,' '
94. call writechar
95. inc edx
96. jmp l1
97. l2:
98. call crlf
99. jmp final
100. 
101. l0: ;else
102. mov edx,2;edx=i
103. l3: ;for
104. cmp edx,n
105. ja final
106. mov eax,1
107. cmp [edi+4*edx],eax
108. je l4
109. mov eax,ebx
110. dec eax;eax=cur-1
111. mov eax,[ecx+4*eax]
112. add eax,edx
113. mov eax,[esi+4*eax]
114. cmp eax,1
115. jne l4
116. mov [ecx+ebx*4],edx
117. mov eax,1
118. mov [edi+edx*4],eax
119. mov eax,ebx
120. inc eax;eax=cur+1
121. push eax
122. call dfs
123. mov eax,0
124. mov [edi+4*edx],eax
125. l4:
126. inc edx
127. jmp l3
128. final:
129. popad
130. pop ebp
131. ret 4
132. dfs ENDP
133. END main

效果

四、迷宫问题

问题描述

有一个 7 x 7 的迷宫,起点是'S',终点是'E',墙是'o',道路是空格。

请找出从起点到终点的通路,通路用符号'.'表示。

用二维数组表示迷宫场景。其中用2代表迷宫的墙壁,0代表可行通道。

走的路径记作1,也就是数组中的0被改为1

c代码

1. #include <stdio.h>
2. #include <stdlib.h>
3. #define M 9
4. //把7*7迷宫加大成9*9格局
5. int maze[M][M] ={
6.         {2,2,2,2,2,2,2,2,2},
7.         {2,0,0,0,0,0,0,0,2},
8.         {2,0,2,2,0,2,2,0,2},
9.         {2,0,2,0,0,2,0,0,2},
10.         {2,0,2,0,2,0,2,0,2},
11.         {2,0,0,0,0,0,2,0,2},
12.         {2,2,0,2,2,0,2,2,2},
13.         {2,0,0,0,0,0,0,0,2},
14.         {2,2,2,2,2,2,2,2,2}
15. };
16. 
17. int start1=1,start2=1;          //假定[1][1]是入口
18. int end1=7,  end2=7;            //假定[7][7]是出口
19. 
20. void visit(int i,int j){
21. int m,n;
22.   maze[i][j] = 1;
23. if(i==end1 && j==end2) { //判断是否到达出口位置,到达直接输出
24. printf("\n显示路径:\n");
25. for(m=0;m<M;m++){
26. for(n=0;n<M;n++){
27. if(maze[m][n] == 2)  printf("o");
28. else if(maze[m][n] == 1)  printf(".");
29. else     printf(" ");           
30.                   }
31. printf("\n");
32.               }//end for
33.    }//end if
34. 
35. //不再判定是否到达出口,只分析老鼠可以在迷宫移动的方向,
36.   //并递归求下一步.
37. if(maze[i][j+1] == 0)    visit(i,j+1);
38. if(maze[i+1][j] == 0)    visit(i+1,j);
39. if(maze[i][j-1] == 0)    visit(i,j-1);
40. if(maze[i-1][j] == 0)    visit(i-1,j);
41.   //若代码运行到这一步,则证明前面走的路径并不能到达出口,
42.   //则返回,把走过的位置重新写作0
43.         maze[i][j] = 0;
44. }
45. 
46. int main (){
47. int i,j;
48. printf("显示迷宫:\n");
49. for(i=0;i<M;i++)   {  /对摆放的数组迷宫进行打印
50. for(j=0;j<M;j++)
51. if(maze[i][j] == 2)   printf("o");
52. else    printf(" ");
53. printf("\n");
54.        }
55. visit(start1,start2);  //直接调用visit函数,把输出内容放在visit函数中,
56.   //好让所有路径进行遍历
57. 
58. return 0;
59. }

汇编代码

INCLUDE Irvine32.inc

.data

ar dd 2,2,2,2,2,2,2,2,2

  dd 2,0,0,0,0,0,0,0,2

  dd 2,0,2,2,0,2,2,0,2

  dd 2,0,2,0,0,2,0,0,2

  dd 2,0,2,0,2,0,2,0,2

  dd 2,0,0,0,0,0,2,0,2

  dd 2,2,0,2,2,0,2,2,2

  dd 2,0,0,0,0,0,0,0,2

  dd 2,2,2,2,2,2,2,2,2

st1 db '显示迷宫:',0

M dd 9

num dd 36

start1 dd 1

start2 dd 1

end1 dd 7

end2 dd 7

.code

main PROC

mov ebx,0;ebx=i

l0:

cmp ebx,M

jae l1

mov ecx,0;ecx=j

l3:

cmp ecx,M

jae l2

push ecx

push ebx

call find

cmp eax,2

jnz l4

mov al,'o'

call writechar

jmp l5

l4:;else

mov al,' '

call writechar

l5:

inc ecx

jmp l3

l2:

call crlf

inc ebx

jmp l0

l1:

push start1

push start2

call visit

final:

  exit

main ENDP

visit PROC

;push i,push j

push ebp

mov ebp,esp

pushad

mov ebx,[ebp+8] ;ebx=j

mov ecx,[ebp+12];ecx=i

               ;edx=m

               ;esi=n

push 1

push ebx

push ecx

call wri

cmp ecx,end1

jne l0

cmp ebx,end2

jne l0

mov edx,0

l1:;for

cmp edx,M

jae l0

mov esi,0

l3:;for2

cmp esi,M

jae l2

push esi

push edx

call find

cmp eax,2

jnz l5

mov al,'o'

call writechar

jmp l4

l5:

cmp eax,1

jnz l6

mov al,'.'

call writechar

jmp l4

l6:

mov al,' '

call writechar

l4:

inc esi

jmp l3

l2:

call crlf

inc edx

jmp l1

l0:;end if

mov eax,ebx

inc eax

push eax

push ecx

call find

cmp eax,0

jne f1

mov eax,ebx

inc eax

push ecx

push eax

call visit

f1:

push ebx

mov eax,ecx

inc eax

push eax

call find

cmp eax,0

jne f2

mov eax,ecx

inc eax

push eax

push ebx

call visit

f2:

mov eax,ebx

dec eax

push eax

push ecx

call find

cmp eax,0

jne f3

mov eax,ebx

dec eax

push ecx

push eax

call visit

f3:

push ebx

mov eax,ecx

dec eax

push eax

call find

cmp eax,0

jne f4

mov eax,ecx

dec eax

push eax

push ebx

call visit

f4:

push 0

push ebx

push ecx

call wri

final:

popad

pop ebp

ret 8

visit ENDP

find PROC

;ar[i][j]

;push j,push i

push ebp

mov ebp,esp

sub esp,4

pushad

mov ebx,[ebp+8];ebx=i

mov ecx,[ebp+12];ecx=j

mov eax,ebx

mul num

mov eax,ar[eax+ecx*4]

mov [ebp-4],eax

popad

mov eax,[ebp-4]

add esp,4

pop ebp

ret 8

find ENDP

wri PROC

;n,ar[i][j]

;push n,push j,push i

push ebp

mov ebp,esp

pushad

mov ebx,[ebp+8];ebx=i

mov ecx,[ebp+12];ecx=j

mov edi,[ebp+16];edi=n

mov eax,ebx

mul num

mov ar[eax+ecx*4],edi

popad

pop ebp

ret 12

wri ENDP

END main

效果

目录
相关文章
|
6月前
|
C语言
【汇编语言实战】输入一个无符号整数求其逆序
【汇编语言实战】输入一个无符号整数求其逆序
46 2
|
6月前
|
C语言
【汇编语言实战】正整数的素数分解
【汇编语言实战】正整数的素数分解
38 1
|
5月前
|
程序员 索引
逆向学习汇编篇:内存管理与寻址方式
逆向学习汇编篇:内存管理与寻址方式
51 0
|
6月前
|
C语言
【汇编语言实战】解迷宫问题
【汇编语言实战】解迷宫问题
51 2
|
6月前
|
算法 C语言 网络架构
【汇编语言实战】整数拆分问题
【汇编语言实战】整数拆分问题
43 2
|
6月前
|
C语言
【汇编语言实战】使用插入排序对给定的数组排序(用栈传递参数)
【汇编语言实战】使用插入排序对给定的数组排序(用栈传递参数)
36 1
|
6月前
|
C语言
【汇编语言实战】输入10个整数求最大值
【汇编语言实战】输入10个整数求最大值
72 1
|
6月前
|
存储
探究汇编中的栈帧和局部变量
探究汇编中的栈帧和局部变量
53 3
|
6月前
|
C语言
【汇编语言实战】输入2个整数求最大公约数
【汇编语言实战】输入2个整数求最大公约数
45 0
|
6月前
|
C语言
【汇编语言实战】已知10个整数求最大值
【汇编语言实战】已知10个整数求最大值
36 0