#pragma once
#include
#include
#include
#define MAZE_ROW 6
#define MAZE_COL 6
typedef struct Maze {
int map[MAZE_ROW][MAZE_COL];
}Maze;
#define FOR_MAZE
#ifdef FOR_MAZE
typedef struct Point {
int row;
int col;
}Point;
typedef Point SeqStackType;
#else
typedef char SeqStackType;
#endif
#define SeqStackMaxSize 1000
typedef struct SeqStack {
SeqStackType data[SeqStackMaxSize];
size_t size;
} SeqStack;
void SeqStackInit(SeqStack* stack);
void SeqStackDestory(SeqStack* stack);
void SeqStackPush(SeqStack* stack, SeqStackType value);
void SeqStackPop(SeqStack* stack);
int GetTop(SeqStack* stack, SeqStackType* value);
size_t SeqStackSize(SeqStack* stack);
void SeqStackAssign(SeqStack* from, SeqStack* to);
#ifdef FOR_MAZE
void SeqStackDebugPrintPoint(SeqStack* stack, const char* msg);
#endif
#include"SeqStack.h"
void SeqStackInit(SeqStack* stack) {
if (stack == NULL) {
return;
}
stack->size = 0;
}
void SeqStackDestory(SeqStack* stack) {
if (stack == NULL) {
return;
}
stack->size = 0;
}
void SeqStackPush(SeqStack* stack, SeqStackType value) {
if (stack == NULL) {
return;
}
if (stack->size >= SeqStackMaxSize)
return;
stack->data[stack->size++] = value;
}
void SeqStackPop(SeqStack* stack) {
if (stack == 0) {
return;
}
if (stack->size == 0)
return;
--stack->size;
}
int GetTop(SeqStack* stack, SeqStackType* value) {
if (stack == NULL || value == NULL) {
return 0;
}
if (stack->size == 0)
return 0;
*value = stack->data[stack->size - 1];
return 1;
}
size_t SeqStackSize(SeqStack* stack) {
if (stack == NULL) {
return 0;
}
return stack->size;
}
void SeqStackAssign(SeqStack* from, SeqStack* to) {
if (from == NULL || to == NULL) {
return;
}
to->size = from->size;
size_t i = 0;
for (; i < from->size; ++i) {
to->data[i] = from->data[i];
}
}
#ifdef FOR_MAZE
#include
void SeqStackDebugPrintPoint(SeqStack* stack, const char* msg) {
if (stack == NULL) {
printf("stack == NULL\n");
return;
}
printf("\n[%s]\n", msg);
printf("[栈底]\n");
size_t i = 0;
for (; i < stack->size; ++i) {
printf("(%d, %d)\n", stack->data[i].row, stack->data[i].col);
}
printf("[栈顶]\n");
}
#endif
void MazeInit(Maze* maze) {
if (maze == NULL) {
return;
}
int map[MAZE_ROW][MAZE_COL] = {
{0, 1, 0, 0, 0, 0},
{0, 1, 1, 1, 0, 0},
{0, 1, 0, 1, 1, 0},
{0, 1, 1, 0, 0, 0},
{0, 0, 1, 0, 0, 0},
{0, 0, 1, 0, 0, 0}
};
size_t i = 0;
for (; i < MAZE_ROW; ++i) {
size_t j = 0;
for (; j < MAZE_COL; ++j) {
maze->map[i][j] = map[i][j];
}
}
}
void MazeInitMultiExit(Maze* maze) {
if (maze == NULL) {
return;
}
int map[MAZE_ROW][MAZE_COL] = {
{ 0, 1, 0, 0, 0, 0 },
{ 0, 1, 1, 1, 0, 0 },
{ 0, 1, 0, 1, 1, 1 },
{ 1, 1, 1, 0, 0, 0 },
{ 0, 0, 1, 0, 0, 0 },
{ 0, 0, 1, 0, 0, 0 }
};
size_t i = 0;
for (; i < MAZE_ROW; ++i) {
size_t j = 0;
for (; j < MAZE_COL; ++j) {
maze->map[i][j] = map[i][j];
}
}
}
void MazeInitMultiExitWithCycle(Maze* maze) {
if (maze == NULL) {
return;
}
int map[MAZE_ROW][MAZE_COL] = {
{ 0, 1, 0, 0, 0, 0 },
{ 0, 1, 1, 1, 0, 0 },
{ 0, 1, 0, 1, 1, 1 },
{ 1, 1, 1, 1, 0, 0 },
{ 0, 0, 1, 0, 0, 0 },
{ 0, 0, 1, 0, 0, 0 }
};
size_t i = 0;
for (; i < MAZE_ROW; ++i) {
size_t j = 0;
for (; j < MAZE_COL; ++j) {
maze->map[i][j] = map[i][j];
}
}
}
void MazePrint(Maze* maze) {
if (maze == NULL) {
return;
}
size_t i = 0;
for (; i < MAZE_ROW; ++i) {
size_t j = 0;
for (; j < MAZE_COL; ++j) {
printf("%2d ", maze->map[i][j]);
}
printf("\n");
}
printf("\n");
}
int CanStay(Maze* maze, Point cur) {
if (maze == NULL) {
return 0;
}
if (cur.row < 0 || cur.row >= MAZE_ROW||
cur.col < 0 || cur.col >= MAZE_COL) {
return 0;
}
if (maze->map[cur.row][cur.col] == 1) {
return 1;
}
return 0;
}
void Mark(Maze* maze, Point cur) {
if (maze == NULL) {
return;
}
maze->map[cur.row][cur.col] = 2;
}
int IsExit(Point cur, Point entry) {
if (cur.row == 0 || cur.col == 0 ||
cur.row == MAZE_ROW - 1 || cur.col == MAZE_COL - 1) {
if (cur.row == entry.row && cur.col == entry.col) {
return 0;
}
return 1;
}
return 0;
}
void _HasPath(Maze* maze, Point cur, Point entry) {
if (maze == NULL) {
return;
}
if (!CanStay(maze, cur)) {
return;
}
Mark(maze, cur);
if (IsExit(cur, entry)) {
printf("找到了路径!\n");
return;
}
Point up = cur;
up.row -= 1;
_HasPath(maze, up, entry);
Point right = cur;
right.col += 1;
_HasPath(maze, right, entry);
Point down = cur;
down.row += 1;
_HasPath(maze, down, entry);
Point left = cur;
left.col -= 1;
_HasPath(maze, left, entry);
return;
}
void HasPath(Maze* maze, Point entry) {
if (maze == NULL) {
return;
}
_HasPath(maze, entry, entry);
}
void HasPathByLoop(Maze* maze, Point entry) {
if (maze == NULL) {
return;
}
if (!CanStay(maze, entry)) {
return;
}
Mark(maze, entry);
SeqStack stack;
SeqStackInit(&stack);
SeqStackPush(&stack, entry);
Point cur;
while (GetTop(&stack, &cur)) {
if (IsExit(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);
}
return;
}
void _GetShortPath(Maze* maze, Point cur, Point entry,
SeqStack* cur_path, SeqStack* short_path) {
if (!CanStay(maze, cur)) {
return;
}
Mark(maze, cur);
SeqStackPush(cur_path, cur);
if (IsExit(cur, entry)) {
SeqStackDebugPrintPoint(cur_path, "找到一条路径!");
if (SeqStackSize(cur_path) < SeqStackSize(short_path)
|| SeqStackSize(short_path) == 0) {
SeqStackAssign(cur_path, short_path);
printf("当前路径是一条比较短的路径\n");
}
SeqStackPop(cur_path);
return;
}
Point up = cur;
up.row -= 1;
_GetShortPath(maze, up, entry, cur_path, short_path);
Point right = cur;
right.col += 1;
_GetShortPath(maze, right, entry, cur_path, short_path);
Point down = cur;
down.row += 1;
_GetShortPath(maze, down, entry, cur_path, short_path);
Point left = cur;
left.col -= 1;
_GetShortPath(maze, left, entry, cur_path, short_path);
SeqStackPop(cur_path);
return;
}
void GetShortPath(Maze* maze, Point entry) {
SeqStack short_path;
SeqStack cur_path;
SeqStackInit(&short_path);
SeqStackInit(&cur_path);
_GetShortPath(maze, entry, entry, &cur_path, &short_path);
SeqStackDebugPrintPoint(&short_path, "最短路径是");
}
int CanStayWithCycle(Maze* maze, Point cur, Point pre) {
if (cur.row < 0 || cur.row >= MAZE_ROW ||
cur.col < 0 || cur.col >= MAZE_COL) {
return 0;
}
int cur_value = maze->map[cur.row][cur.col];
if (cur_value == 1) {
return 1;
}
if (pre.row >= 0 && pre.row < MAZE_ROW &&
pre.col >= 0 && pre.col < MAZE_COL) {
int pre_value = maze->map[pre.row][pre.col];
if (cur_value - 1 > pre_value) {
return 1;
}
}
return 0;
}
void MarkWithCycle(Maze* maze, Point cur, Point pre) {
if (pre.row < 0 || pre.row >= MAZE_ROW ||
pre.col < 0 || pre.col >= MAZE_COL) {
maze->map[cur.row][cur.col] = 2;
return;
}
int pre_value = maze->map[pre.row][pre.col];
maze->map[cur.row][cur.col] = pre_value + 1;
}
void _GetShortPathWithCycle(Maze* maze, Point cur, Point pre, Point entry,
SeqStack* cur_path, SeqStack* short_path) {
if (!CanStayWithCycle(maze, cur, pre)) {
return;
}
MarkWithCycle(maze, cur, pre);
SeqStackPush(cur_path, cur);
if (IsExit(cur, entry)) {
SeqStackDebugPrintPoint(cur_path, "找到一条路径!");
if (SeqStackSize(cur_path) < SeqStackSize(short_path)
|| SeqStackSize(short_path) == 0) {
SeqStackAssign(cur_path, short_path);
}
SeqStackPop(cur_path);
return;
}
Point up = cur;
up.row -= 1;
_GetShortPathWithCycle(maze, up, cur, entry, cur_path, short_path);
Point right = cur;
right.col += 1;
_GetShortPathWithCycle(maze, right, cur, entry, cur_path, short_path);
Point down = cur;
down.row += 1;
_GetShortPathWithCycle(maze, down, cur, entry, cur_path, short_path);
Point left = cur;
left.col -= 1;
_GetShortPathWithCycle(maze, left, cur, entry, cur_path, short_path);
SeqStackPop(cur_path);
return;
}
void GetShortPathWithCycle(Maze* maze, Point entry) {
SeqStack short_path;
SeqStack cur_path;
SeqStackInit(&short_path);
SeqStackInit(&cur_path);
Point pre = { -1, -1 };
_GetShortPathWithCycle(maze, entry, pre, entry, &cur_path, &short_path);
SeqStackDebugPrintPoint(&short_path, "最短路径是");
}
#define TEST_HEADER printf("\n======%s======\n", __FUNCTION__)
void Test1() {
TEST_HEADER;
Maze maze;
MazeInit(&maze);
MazePrint(&maze);
}
void Test2() {
TEST_HEADER;
Maze maze;
MazeInit(&maze);
Point entry = { 0, 1 };
HasPath(&maze, entry);
MazePrint(&maze);
}
void Test3() {
TEST_HEADER;
Maze maze;
MazeInit(&maze);
Point entry = { 0, 1 };
HasPathByLoop(&maze, entry);
MazePrint(&maze);
}
void Test4() {
TEST_HEADER;
Maze maze;
MazeInitMultiExit(&maze);
Point entry = { 0, 1 };
GetShortPath(&maze, entry);
MazePrint(&maze);
}
void Test5() {
TEST_HEADER;
Maze maze;
MazeInitMultiExitWithCycle(&maze);
Point entry = { 0, 1 };
GetShortPathWithCycle(&maze, entry);
MazePrint(&maze);
}
int main() {
Test1();
Test2();
Test3();
Test4();
Test5();
system("pause");
return 0;
}