定义迷宫
#include "seqstack.h"
#define MAX_ROW 6 //最大行数
#define MAX_COL 6 //最大列数
typedef struct Maze{
int map[MAX_ROW][MAX_COL];//定义地图
}Maze;
void MazeInit(Maze* maze){//迷宫求解
int map[MAX_ROW][MAX_COL]={
{ 0, 1, 0, 0, 0, 0 },
{ 0, 1, 1, 1, 0, 0 },
{ 0, 1, 1, 1, 1, 0 },
{ 0, 1, 1, 1, 0, 0 },
{ 0, 1, 1, 1, 0, 0 },
{ 0, 0, 0, 1, 0, 0 },
};
size_t i = 0;
for(;i<MAX_ROW;++i){
size_t j = 0;
for(;j<MAX_COL;++j){
maze->map[i][j] = map[i][j];
}
}
}
void MazePrint(Maze* maze){//迷宫打印
size_t i = 0;
for(;i<MAX_ROW;++i){
size_t j = 0;
for(;j<MAX_COL;++j){
printf("%2d ",maze->map[i][j]);
}
printf("\n");
}
printf("\n");
}
引用头文件
#pragma once
#include <stdio.h>
#include <stdlib.h>
#define FOR_MAZE
#ifdef FOR_MAZE
typedef struct Point{
int row;
int col;
}Point;
typedef Point SeqStackType;
#else
typedef char SeqStackType;
#endif
typedef struct SeqStack{
SeqStackType* data;
size_t size;
size_t capacity;
}SeqStack;
void SeqStackInit(SeqStack* s);//栈初始化
void SeqStackPush(SeqStack* s,SeqStackType value);//压栈
void SeqStackReSize(SeqStack* s);//更改大小
void SeqStackPop(SeqStack* s);//出栈
int SeqStackTop(SeqStack* s,SeqStackType* value);//取栈顶元素
void SeqStackDestroy(SeqStack* s);//销毁
递归版本
//////////////////////////////////////////////////////////////////////////////////////
// Round1 递归版本
/////////////////////////////////////////////////////////////////////////////////////
//是否能落脚,能返回1,不能返回0
int CanStay(Maze* maze,Point pt){
//判断点是否在地图上
if(pt.row < 0 || pt.row >= MAX_ROW || pt.col < 0 || pt.col >= MAX_COL){
return 0;
}
int value = maze->map[pt.row][pt.col];
if(value == 1){
return 1;
}
return 0;
}
void Mark(Maze* maze,Point cur){
maze->map[cur.row][cur.col] = 2;
return;
}
int IsExit(Maze* maze,Point cur,Point entry){
(void)maze;
//如果当前点到了边界,即为找到了出口,但是不能是入口点
if(cur.row == entry.row && cur.col == entry.col){
return 0;
}
if(cur.row == 0 || cur.row == MAX_ROW-1 || cur.col == 0 || cur.col == MAX_COL-1){
return 1;
}
return 0;
}
void _GetPath(Maze* maze,Point cur,Point entry){
printf("row:%d col:%d\n",cur.row,cur.col);
//1.判断当前点是否能落脚,不能落脚直接返回
if(!CanStay(maze,cur)){
return;
}
//2.如果能落脚,标记当前点
Mark(maze,cur);
//3.判断当前点是否为出口点,是则直接return
if(IsExit(maze,cur,entry)){
//找到了出口直接返回
printf("找到了一条出路\n");
return;
}
//4.判断当前点的上下左右是否有路可走,递归判断
Point up = cur;
up.row -= 1;
_GetPath(maze,up,entry);
Point right = cur;
right.col += 1;
_GetPath(maze,right,entry);
Point down = cur;
down.row += 1;
_GetPath(maze,down,entry);
Point left = cur;
left.col -= 1;
_GetPath(maze,left,entry);
}
void GetPath(Maze* maze,Point entry){
if(maze == NULL){
return;
}
//使用_GetPath辅助完成递归
_GetPath(maze,entry,entry);
}
非递归版本
//////////////////////////////////////////////////////////////////////////////////////
// Round2 使用非递归版本
/////////////////////////////////////////////////////////////////////////////////////
void GetPathByLoop(Maze* maze,Point entry){
if(maze == NULL){
return;
}
SeqStackType cur;
//手动维护一个栈,保存走过的路径
SeqStack stack;
SeqStackInit(&stack);
//1.先判断是否能落脚,能落脚,当前点入栈
if(!CanStay(maze,entry)){
return;
}
SeqStackPush(&stack,entry);
//2.如果能落脚,标记当前点
// Mark(maze,entry);
//循环取栈顶元素
while(SeqStackTop(&stack,&cur)){
Mark(maze,cur);
if(IsExit(maze,cur,entry)){
printf("找到了一条出路\n");
return;
}
Point up = cur;
up.row -= 1;
if(CanStay(maze,up)){
// Mark(maze,up);
SeqStackPush(&stack,up);
continue;
}
Point right = cur;
right.col += 1;
if(CanStay(maze,right)){
// Mark(maze,right);
SeqStackPush(&stack,right);
continue;
}
Point down = cur;
down.row += 1;
if(CanStay(maze,down)){
// Mark(maze,down);
SeqStackPush(&stack,down);
continue;
}
Point left = cur;
left.col -= 1;
if(CanStay(maze,left)){
// Mark(maze,left);
SeqStackPush(&stack,left);
continue;
}
SeqStackPop(&stack);
}
}
测试代码
//////////////////////////////////////////////////////////////////////////////////////
// 以下为测试代码
/////////////////////////////////////////////////////////////////////////////////////
#if 1
#define TEST_HEADER printf("\n=========================%s=======================\n",__FUNCTION__)
void test(){
TEST_HEADER;
Maze maze;
MazeInit(&maze);
MazePrint(&maze);
Point entry = {0,1};
GetPath(&maze,entry);
MazePrint(&maze);
}
void test2(){
TEST_HEADER;
Maze maze;
MazeInit(&maze);
MazePrint(&maze);
Point entry = {0,1};
GetPathByLoop(&maze,entry);
MazePrint(&maze);
}
int main(){
test();
test2();
return 0;
}
#endif