迷宫问题求解
合集下载
相关主题
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
1、 用户输入迷宫的高度和宽度。 2、 根据用户输入显示生成的迷宫或者错误提示信息。 3、 求出从迷宫出口到入口的最短路径。 4、 显示该路径,或者无解信息。
关键字:迷宫、最短路径、动态规划、Dijkstra算法 引言:
寻径问题(最短路径)是图论研究中的一个经典算法问题,旨在寻 找图(由结点和路径组成)中两结点之间的最短路径。该问题不论是在 现实(比如火星探测)还是在网络中(比如各种游戏),都具有重大意 义。
需求分析:
1、用户输入迷宫的高度和宽度。 2、根据用户输入显示生成的迷宫或者错误提示信息。 3、求出从迷宫出口到入口的最短路径。 4、显示该路径,或者无解信息。
数据结构设计:
char **maze; char ***path; char **toBeChoosed; int **weight; 录。 //迷宫,0表示障碍,非0表示可通过。 //存储每个点到入口的路径。 //待选择的结点。 //搜索到的已知的每个点到入口最短距离的记
{ case 0://左。。 *dx = 0; *dy = 1; break; case 1://下。。 *dx = 1; *dy = 0; break; case 2://右。。 *dx = 0; *dy = -1; break; case 3://上。。 *dx = -1; *dy = 0; break; default: *dx = 0; *dy = 0; break; } } //判断该点是否是合法的,不越界。。 int IsInMaze(int x, int y) {
{ char **maze;//迷宫,0表示障碍,非0表示可通过。。 char ***path;//存储每个点到入口的路径。。 char **toBeChoosed;//待选择的结点。。 int **weight;//搜索到的已知的每个点到入口最短距离的记录。。 int *record;//已知最佳结点的记录。。 int count;//已知最佳结点个数。。 int x, y, dx, dy, x1, y1; int index; int bestPoint, bestWeight, bestValue;//在未选择的节点中所选择的最佳 节点。。 char again; int i, j; again = 'y'; while (again == 'y')//用户选择继续。。 { system("cls");//清屏。。 printf("Height = "); scanf("%d", &height);//输入迷宫高度。。 printf("Width = "); scanf("%d", &width);//输入迷宫宽度。。 if ((height <= 0) || (width <= 0) || (height * width > 40000)) { printf("[ Height>0 ] && [ Width>0 ] && [ Height*Width<=40000 ]\n"); printf("Please input again..\n");
int *record; int count;
//已知最佳结点的记录。 //已知最佳结点个数。
算法设计:
#include <stdio.h> #include <stdlib.h> #include <time.h> #include <conio.h> #include <string.h> #define START_X 1 #define START_Y width/2 //入口横纵坐标。。 #define END_X height #define END_Y width/2 //出口横纵坐标。。 #define MAX_W 32767 //权值上限。。 int width, height;//迷宫的宽和高。。 char ico[10][3] = {"■", "─", "│", "┌", "┐", "┘", "└", "□", "入", "出"};//各个 符号。。 int icoIndex[4][4] = { 1, 4, 0, 5, 6, 2, 5, 0, 0, 3, 1, 6, 3, 0, 4, 2 };//对应方向的 路标。。 //获取二维数组下标偏移量。。 void GetDxDy(int i, int *dx, int *dy) { switch (i)
for (j = 0; j < width; j++) { printf("%s", ico[maze[i][j]]);//输出原始迷宫。。 } printf("\n"); } printf("Press any key to continue..\n"); getch(); /**********************搜索路径**********************/ count = 0; bestPoint = ConvertToIndex(START_X - 1, START_Y - 1);//起点设为 最佳节点。。 weight[START_X - 1][START_Y - 1] = 0;//起点权值为0。。 do { ConvertToXY(bestPoint, &x1, &y1); toBeChoosed[x1][y1] = 0; record[count] = bestPoint;//将最佳节点记录下来。。 count++; for (i = 0; i < 4; i++)//更新最佳节点周围4个点的权值大小。。 { GetDxDy(i, &dx, &dy); x = x1 + dx; y = y1 + dy; if (IsInMaze(x, y) && toBeChoosed[x][y])//如果是合法的点,而 且是待选择的点。。
{ if (weight[x][y] > weight[x1][y1] + 1)//权值变小。。 { weight[x][y] = weight[x1][y1] + 1;//更新权值。。 strcpy(path[x][y], path[x1][y1]);//更新路径。。 path[x][y][strlen(path[x1][y1])] = i + 48;//添加路径。。 path[x][y][strlen(path[x1][y1]) + 1] = '\0'; } } } if (bestPoint == ConvertToIndex(END_X - 1, END_Y - 1))//如果到 出口就退出。。 { break; } bestPoint = -1; bestWeight = MAX_W; for (i = 0; i < count; i++)//在所有最佳节点的周围选择一个新的最 佳节点。。 { index = record[i]; ConvertToXY(index, &x1, &y1); for (j = 0; j < 4; j++) { GetDxDy(j, &dx, &dy); x = x1 + dx; y = y1 + dy;
if ((x < 0) || (x >= height) || (y < 0) || (y >= width)) { return (0); } return (1); } //一维转为二维。。 void ConvertToXY(int index, int *x, int *y) { *x = index / width; *y = index % width; } //二维转为一维。。 int ConvertToIndex(int x, int y) { return (x * width + y); } //求绝对值。。 int Abs(int a) { return ((a >= 0) ? a : -a); } int main(void)
课程设计任务书
学生姓名: 专业班级: 指导教师: 夏红霞 工作单位: 技术学院 题 目: 迷宫问题求解 Βιβλιοθήκη Baidu程设计要求: 计算机科学与
1、熟练掌握基本的数据结构; 2、熟练掌握各种算法; 3、运用高级语言编写质量高、风格好的应用程序。
课程设计任务:
1、系统应具备的功能: (1)用随机函数建立一个迷宫,给定出入口 (2)设计一个模拟走迷宫的程序寻找通路,存在则将其显示在 屏幕上 (3)找出其中途径最短的通路 2、数据结构设计; 3、主要算法设计; 4、编程及上机实现; 5、撰写课程设计报告,包括: (1)设计题目; (2)摘要和关键字; (3)正文,包括引言、需求分析、数据结构设计、算法设计、程序 实现及测试、不足之处、设计体会等; (4)结束语; (5)参考文献。
时间安排: 2010年7月5日-9日 (第19周)
7月5日 7月6日 7月7-8日 7月9日 7月10日 查阅资料 系统设计,数据结构设计,算法设计 编程并上机调试 撰写报告 验收程序,提交设计报告书。
指导教师签名:
2010年7月4日 系主任(或责任教师)签名: 7月4日
2010年
迷宫问题求解
摘要:该程序主要由以下几部分构成:
printf("Height = "); scanf("%d", &height); printf("Width = "); scanf("%d", &width); } /**********************分配相应内存空间 **********************/ maze = (char**)malloc(sizeof(char*) * height); toBeChoosed = (char**)malloc(sizeof(char*) * height); for (i = 0; i < height; i++) { maze[i] = (char*)malloc(sizeof(char) * width); toBeChoosed[i] = (char*)malloc(sizeof(char) * width); } weight = (int**)malloc(sizeof(int) * height); for (i = 0; i < height; i++) { weight[i] = (int*)malloc(sizeof(int) * width);; } path = (char***)malloc(sizeof(char**) * height); for (i = 0; i < height; i++) { path[i] = (char**)malloc(sizeof(char*) * width);; for (j = 0; j < width; j++) { path[i][j] = (char*)malloc(sizeof(char) * height * width);
path[i][j][0] = '\0'; } } record = (int*)malloc(sizeof(int) * height * width); /**********************随机生成迷宫,并显示 **********************/ srand((unsigned)time(NULL));//设置随机数种子。。 for (i = 0; i < height; i++) { for (j = 0; j < width; j++) { maze[i][j] = rand() % 3;//0表示障碍,非0表示可通过,通路:障 碍 = 2:1。。 maze[i][j] = (maze[i][j]) ? 7 : 0;//障碍物与通路的图标。。 toBeChoosed[i][j] = maze[i][j]; weight[i][j] = MAX_W; } } maze[START_X - 1][START_Y - 1] = 8;//起点图标。。 toBeChoosed[START_X - 1][START_Y - 1] = maze[START_X - 1] [START_Y - 1]; maze[END_X - 1][END_Y - 1] = 9;//终点图标。。 toBeChoosed[END_X - 1][END_Y - 1] = maze[END_X - 1][END_Y 1]; for (i = 0; i < height; i++) {
关键字:迷宫、最短路径、动态规划、Dijkstra算法 引言:
寻径问题(最短路径)是图论研究中的一个经典算法问题,旨在寻 找图(由结点和路径组成)中两结点之间的最短路径。该问题不论是在 现实(比如火星探测)还是在网络中(比如各种游戏),都具有重大意 义。
需求分析:
1、用户输入迷宫的高度和宽度。 2、根据用户输入显示生成的迷宫或者错误提示信息。 3、求出从迷宫出口到入口的最短路径。 4、显示该路径,或者无解信息。
数据结构设计:
char **maze; char ***path; char **toBeChoosed; int **weight; 录。 //迷宫,0表示障碍,非0表示可通过。 //存储每个点到入口的路径。 //待选择的结点。 //搜索到的已知的每个点到入口最短距离的记
{ case 0://左。。 *dx = 0; *dy = 1; break; case 1://下。。 *dx = 1; *dy = 0; break; case 2://右。。 *dx = 0; *dy = -1; break; case 3://上。。 *dx = -1; *dy = 0; break; default: *dx = 0; *dy = 0; break; } } //判断该点是否是合法的,不越界。。 int IsInMaze(int x, int y) {
{ char **maze;//迷宫,0表示障碍,非0表示可通过。。 char ***path;//存储每个点到入口的路径。。 char **toBeChoosed;//待选择的结点。。 int **weight;//搜索到的已知的每个点到入口最短距离的记录。。 int *record;//已知最佳结点的记录。。 int count;//已知最佳结点个数。。 int x, y, dx, dy, x1, y1; int index; int bestPoint, bestWeight, bestValue;//在未选择的节点中所选择的最佳 节点。。 char again; int i, j; again = 'y'; while (again == 'y')//用户选择继续。。 { system("cls");//清屏。。 printf("Height = "); scanf("%d", &height);//输入迷宫高度。。 printf("Width = "); scanf("%d", &width);//输入迷宫宽度。。 if ((height <= 0) || (width <= 0) || (height * width > 40000)) { printf("[ Height>0 ] && [ Width>0 ] && [ Height*Width<=40000 ]\n"); printf("Please input again..\n");
int *record; int count;
//已知最佳结点的记录。 //已知最佳结点个数。
算法设计:
#include <stdio.h> #include <stdlib.h> #include <time.h> #include <conio.h> #include <string.h> #define START_X 1 #define START_Y width/2 //入口横纵坐标。。 #define END_X height #define END_Y width/2 //出口横纵坐标。。 #define MAX_W 32767 //权值上限。。 int width, height;//迷宫的宽和高。。 char ico[10][3] = {"■", "─", "│", "┌", "┐", "┘", "└", "□", "入", "出"};//各个 符号。。 int icoIndex[4][4] = { 1, 4, 0, 5, 6, 2, 5, 0, 0, 3, 1, 6, 3, 0, 4, 2 };//对应方向的 路标。。 //获取二维数组下标偏移量。。 void GetDxDy(int i, int *dx, int *dy) { switch (i)
for (j = 0; j < width; j++) { printf("%s", ico[maze[i][j]]);//输出原始迷宫。。 } printf("\n"); } printf("Press any key to continue..\n"); getch(); /**********************搜索路径**********************/ count = 0; bestPoint = ConvertToIndex(START_X - 1, START_Y - 1);//起点设为 最佳节点。。 weight[START_X - 1][START_Y - 1] = 0;//起点权值为0。。 do { ConvertToXY(bestPoint, &x1, &y1); toBeChoosed[x1][y1] = 0; record[count] = bestPoint;//将最佳节点记录下来。。 count++; for (i = 0; i < 4; i++)//更新最佳节点周围4个点的权值大小。。 { GetDxDy(i, &dx, &dy); x = x1 + dx; y = y1 + dy; if (IsInMaze(x, y) && toBeChoosed[x][y])//如果是合法的点,而 且是待选择的点。。
{ if (weight[x][y] > weight[x1][y1] + 1)//权值变小。。 { weight[x][y] = weight[x1][y1] + 1;//更新权值。。 strcpy(path[x][y], path[x1][y1]);//更新路径。。 path[x][y][strlen(path[x1][y1])] = i + 48;//添加路径。。 path[x][y][strlen(path[x1][y1]) + 1] = '\0'; } } } if (bestPoint == ConvertToIndex(END_X - 1, END_Y - 1))//如果到 出口就退出。。 { break; } bestPoint = -1; bestWeight = MAX_W; for (i = 0; i < count; i++)//在所有最佳节点的周围选择一个新的最 佳节点。。 { index = record[i]; ConvertToXY(index, &x1, &y1); for (j = 0; j < 4; j++) { GetDxDy(j, &dx, &dy); x = x1 + dx; y = y1 + dy;
if ((x < 0) || (x >= height) || (y < 0) || (y >= width)) { return (0); } return (1); } //一维转为二维。。 void ConvertToXY(int index, int *x, int *y) { *x = index / width; *y = index % width; } //二维转为一维。。 int ConvertToIndex(int x, int y) { return (x * width + y); } //求绝对值。。 int Abs(int a) { return ((a >= 0) ? a : -a); } int main(void)
课程设计任务书
学生姓名: 专业班级: 指导教师: 夏红霞 工作单位: 技术学院 题 目: 迷宫问题求解 Βιβλιοθήκη Baidu程设计要求: 计算机科学与
1、熟练掌握基本的数据结构; 2、熟练掌握各种算法; 3、运用高级语言编写质量高、风格好的应用程序。
课程设计任务:
1、系统应具备的功能: (1)用随机函数建立一个迷宫,给定出入口 (2)设计一个模拟走迷宫的程序寻找通路,存在则将其显示在 屏幕上 (3)找出其中途径最短的通路 2、数据结构设计; 3、主要算法设计; 4、编程及上机实现; 5、撰写课程设计报告,包括: (1)设计题目; (2)摘要和关键字; (3)正文,包括引言、需求分析、数据结构设计、算法设计、程序 实现及测试、不足之处、设计体会等; (4)结束语; (5)参考文献。
时间安排: 2010年7月5日-9日 (第19周)
7月5日 7月6日 7月7-8日 7月9日 7月10日 查阅资料 系统设计,数据结构设计,算法设计 编程并上机调试 撰写报告 验收程序,提交设计报告书。
指导教师签名:
2010年7月4日 系主任(或责任教师)签名: 7月4日
2010年
迷宫问题求解
摘要:该程序主要由以下几部分构成:
printf("Height = "); scanf("%d", &height); printf("Width = "); scanf("%d", &width); } /**********************分配相应内存空间 **********************/ maze = (char**)malloc(sizeof(char*) * height); toBeChoosed = (char**)malloc(sizeof(char*) * height); for (i = 0; i < height; i++) { maze[i] = (char*)malloc(sizeof(char) * width); toBeChoosed[i] = (char*)malloc(sizeof(char) * width); } weight = (int**)malloc(sizeof(int) * height); for (i = 0; i < height; i++) { weight[i] = (int*)malloc(sizeof(int) * width);; } path = (char***)malloc(sizeof(char**) * height); for (i = 0; i < height; i++) { path[i] = (char**)malloc(sizeof(char*) * width);; for (j = 0; j < width; j++) { path[i][j] = (char*)malloc(sizeof(char) * height * width);
path[i][j][0] = '\0'; } } record = (int*)malloc(sizeof(int) * height * width); /**********************随机生成迷宫,并显示 **********************/ srand((unsigned)time(NULL));//设置随机数种子。。 for (i = 0; i < height; i++) { for (j = 0; j < width; j++) { maze[i][j] = rand() % 3;//0表示障碍,非0表示可通过,通路:障 碍 = 2:1。。 maze[i][j] = (maze[i][j]) ? 7 : 0;//障碍物与通路的图标。。 toBeChoosed[i][j] = maze[i][j]; weight[i][j] = MAX_W; } } maze[START_X - 1][START_Y - 1] = 8;//起点图标。。 toBeChoosed[START_X - 1][START_Y - 1] = maze[START_X - 1] [START_Y - 1]; maze[END_X - 1][END_Y - 1] = 9;//终点图标。。 toBeChoosed[END_X - 1][END_Y - 1] = maze[END_X - 1][END_Y 1]; for (i = 0; i < height; i++) {