迷宫求解(深度优先)

迷宫求解

问题初始条件: 给定一副地图,一个开始坐标,一个结束坐标,寻找一条可以从开始坐标到结束坐标的路径

问题分析: 可以用栈存储路径的坐标且坐标应有横纵两个属性来对应迷宫二维数组中的位置,此外还需要一个属性来确定方向下一个走到的路径的坐标,定义坐标结构体如下:

typedef struct {
	int row;
	int col;
	int walk;//判断方向
}PosType;

问题关键: 如何走迷宫,首先不能走自己已经走过的路,其次不能走地图中不可走的路,当排除这两个条件后在判断这个点剩下可以走的路将该点压入栈,如果走到最后但并没有到达终点说明进入了一个死胡同,则将该点弹出并标记为不可走的点,然后判断上一个点是否可走,以此继续,总结如下

  • 判断该点是否可走
  • 该点走的下一个方向是哪里
  • 走到该点,继续判断
  • 如果出现死路
    • 将该点标记为不可走并弹出
    • 判断目前栈顶元素的点循环上一过程
void mazePath(PosType start, PosType end) {
	PosType temp = start;
	SqStack s;
	InitStack(s);
	while (true) {
		if (temp.col == end.col && temp.row == end.row)
		{
			Push(s, temp);
			PrintRoad(s);//打印栈内元素坐标即路径坐标
			break;
		}
		temp.walk=IsCanPass(temp);//判断应该走的方向
		if (temp.walk!=0)
		{
			mazenum[temp.row][temp.col] = 0;//走完该点后将该点设置为不可走
			Push(s,temp);
			temp = walk_to_next(temp, temp.walk);//按照方向走到该点
		}
		else {
			mazenum[temp.row][temp.col] = 0;//判断该点为死路则标记为不可走
			pop(s, temp);//弹出走到该点的点
			mazenum[temp.row][temp.col] = 1;//将该点标记为可以走,继续寻找
		}
	}
}

完整代码如下:

#include
#include
int mazenum[6][6]= { 
{0,1,0,0,0,0},
{0,1,1,1,1,0},
{0,1,0,1,0,0},
{0,1,0,1,1,0},
{0,1,1,0,1,0},
{0,0,1,1,1,0} };
int len = 6;

typedef struct {
	int row;
	int col;
	int walk;//判断方向
}PosType;

typedef struct {
	PosType* base;  //栈底指针
	PosType* top;   //栈顶指针
	int     stacksize;
} SqStack;

PosType maze[6][6];
#define STACK_INIT_SIZE 100;     //存储空间初始分配量
#define STACKINCREMENT 10;     //存储空间分配增量
void InitStack(SqStack& s) {
	s.base = (PosType*)malloc(100*sizeof(PosType));
	s.top = s.base;
	s.stacksize = 100;
}
void Push(SqStack& s, PosType&e) {
	if (s.top - s.base >= s.stacksize) {
		s.base = (PosType*)realloc(s.base, (100 + 10) * sizeof(PosType));
		s.stacksize += 10;
		s.top = s.base + s.stacksize;
	}
	*s.top = e;
	s.top++;
}
void pop(SqStack& s, PosType& e) {
	if (s.top == s.base) {
		printf("栈为空!\n");
	}
	else
	{
		e = *--s.top;
	}
}
PosType getTop(SqStack &s,PosType &p) {
	p = *(s.top - 1);
	return p;
}
int IsCanPass(PosType &p) {
			if (mazenum[p.row ][p.col+1]&&p.col+1<len)
			{
				return 1;
			}

			else if (mazenum[p.row+1][p.col]&&p.row+1<len)
			{
				return 2;
			}

			else if (mazenum[p.row ][p.col-1]&&p.col-1>0)
			{
				return 3;
			}

			else if (mazenum[p.row-1][p.col]&&p.row-1>0)
			{
				return 4;
			}
			else
			{
				return 0;
			}
 }
PosType walk_to_next(PosType p, int di) {
	if (di==1)
	{
		p.col++;
	}
	else if (di == 2) {
		p.row++;
	}
	else if (di == 3) {
		p.col--;
	}
	else if (di == 4) {
		p.row--;
	}
	else
	{
		printf("方向有误!");
	}
	return p;
}
void PrintRoad(SqStack s) {
	while (s.base != s.top) {
		s.top--;
		printf("(%d,%d)", s.top->row, s.top->col);
	}

}
void mazePath(PosType start, PosType end) {
	PosType temp = start;
	SqStack s;
	InitStack(s);
	while (true) {
		if (temp.col == end.col && temp.row == end.row)
		{
			//printf("找到了");
			Push(s, temp);
			PrintRoad(s);
			break;
		}
		temp.walk=IsCanPass(temp);
		if (temp.walk!=0)
		{
			mazenum[temp.row][temp.col] = 0;
			Push(s,temp);
			//printf("(%d,%d)", temp.row, temp.col);
			temp = walk_to_next(temp, temp.walk);
		}
		else {
			mazenum[temp.row][temp.col] = 0;
			pop(s, temp);
			mazenum[temp.row][temp.col] = 1;
		}
	}
}

void createMaze() {
	for (int i = 0; i < 6; i++)
	{
		for (int j = 0; j < 6; j++) {
			//maze[i][j].Canpass = mazenum[i][j];
			maze[i][j].col = j;
			maze[i][j].row = i;
		}
	}
}

void printMaze() {
	for (int i = 0; i < 6; i++)
	{
		for (int j = 0; j < 6; j++) {
			printf("%d ", mazenum[i][j]);
		}
		printf("\n");
	}
}

void main() {
	createMaze();
	printMaze();
	PosType start, end;
	start.row = 0;
	start.col = 1;
	end.row = 5;
	end.col = 2;
	mazePath(start, end);
	
}

你可能感兴趣的:(Data,Structure,深度优先)