老鼠走迷宫算法中的一点优化

         老鼠走迷宫的算法当中在搜索路线时,有一些位置是死胡同,事先标记出来可以大大减少无效搜索,提高搜索速度。

比如三个方向都是墙壁,只有一个方向可以走通的非起点非终点位置就可以标记出来,在搜索时根本不用再去计算。

 

原始图

 

标记图

 

#include <stdio.h>
#include <conio.h>
#include <stdlib.h>
#ifdef _WIN32
   #include <windows.h>
   void gotoxy(int x, int y);
#endif

void visit(int x, int y);

#define MOUSEMAZE1 1
#define MOUSEMAZE2 1

#ifdef MOUSEMAZE1
#define XSIZE 70
#define YSIZE 22
int maze[YSIZE][XSIZE] =
 {{2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2},
  {2,0,0,0,0,0,0,0,2,2,2,0,0,0,2,0,0,0,2,2,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0,2,0,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,2,2,2,0,0,2,0,2,2,0,2},
  {2,0,2,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,2,2,2,0,0,2,0,0,0,2,2,0,2,0,2,2,2,2,2,2,2,0,0,2,0,0,0,2,2,0,0,2,0,0,0,2,2,0,0,2,2,2,0,0,0,2,0,0,0,2,2},
  {2,0,2,0,0,0,2,0,0,0,2,2,2,2,2,2,2,0,0,2,0,0,0,2,2,0,0,0,0,2,2,2,0,0,0,2,2,2,0,0,0,0,0,2,2,0,2,2,2,2,2,2,2,0,0,2,0,0,0,2,2,0,0,0,0,0,2,2,0,2},
  {2,0,2,0,2,0,2,0,2,0,2,2,0,2,0,0,0,0,2,2,0,0,2,0,0,0,2,2,0,0,0,0,2,2,2,0,0,2,0,2,0,2,2,2,2,2,2,0,0,2,0,0,0,2,2,0,0,0,0,0,0,0,2,0,0,0,2,2,0,2},
  {2,0,2,0,2,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,2,2,2,0,0,2,0,0,0,2,2,0,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,2,2,2,0,0,2,0,0,0,2,2,2,0,0,2,2,0,2,2,0,2},
  {2,0,2,0,2,0,2,0,2,0,0,0,0,0,2,2,0,2,2,2,2,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,2,2,2,0,0,2,2,2,2,2,2,2,0,0,2,0,0,0,0,0,0,2,2,2,0,2,0,0,0,2,2,0,2},
  {2,0,2,0,2,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,2,2,2,0,0,2,0,2,2,0,2,0,0,2,0,0,2,0,2,2,0,0,0,2,2,0,2,2,0,0,0,0,0,0,0,2,0,0,2,0,0,0,2,2,0,2,2,0,2},
  {2,0,2,0,2,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,2,2,2,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,2,2,2,0,0,0,2,0,0,0,0,0,0,0,0,0,0,0,0,2,2,2,0,0,0,0,2,2,0,2},
  {2,0,2,0,2,0,2,0,2,2,0,2,0,0,2,0,2,0,2,0,2,0,0,2,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,2,2,2,0,0,2,0,0,0,2,0,0,0,0,0,2,2,2,0,0,2,0,2,0,0,0,2,2,0,2},
  {2,0,0,0,2,0,0,0,2,2,0,2,0,0,2,0,0,0,2,0,2,0,0,0,2,0,2,0,0,2,2,0,2,2,0,2,0,0,2,2,2,2,2,2,2,0,0,2,0,0,0,0,0,0,0,2,2,2,2,2,2,2,0,0,2,0,2,2,0,2},
  {2,0,2,0,2,0,2,0,2,0,0,2,2,0,2,2,0,2,2,0,2,2,0,0,0,0,2,0,2,0,0,0,2,0,0,0,2,0,2,2,0,0,2,0,2,0,0,2,2,0,0,0,0,0,0,2,2,2,0,2,2,0,0,0,0,0,2,2,0,2},
  {2,2,2,2,2,0,0,0,2,0,0,2,0,0,0,2,0,2,0,0,0,2,0,0,2,2,0,2,2,0,0,0,0,0,2,0,0,2,0,2,0,2,0,0,0,0,2,2,0,2,2,2,2,0,2,2,2,0,0,2,2,0,0,0,0,0,2,2,0,2},
  {2,0,0,0,2,0,0,0,2,0,2,0,2,0,2,0,0,2,2,0,2,2,0,0,2,2,2,2,0,2,0,0,0,0,0,0,0,2,0,0,0,0,0,2,0,0,2,0,2,0,2,0,0,0,2,2,2,0,0,2,2,0,0,0,0,0,0,2,0,2},
  {2,0,0,0,2,0,0,0,2,2,0,0,0,0,2,0,0,2,0,2,0,2,0,0,0,0,2,2,0,2,0,2,0,0,2,0,0,0,2,2,0,0,2,0,2,0,2,0,0,0,0,0,0,0,2,2,2,0,0,2,2,2,2,2,2,2,0,0,2,2},
  {2,2,2,2,2,0,0,0,2,2,0,2,0,0,2,0,2,0,0,0,2,0,0,0,0,0,2,0,2,0,0,2,2,2,2,2,2,2,0,0,0,0,0,0,2,0,0,2,0,2,0,0,0,2,2,2,0,0,0,2,0,0,2,0,2,2,0,0,0,2},
  {2,2,2,2,2,0,0,0,2,2,0,2,0,0,2,0,0,0,2,0,0,0,2,0,2,0,2,0,0,0,2,0,2,2,0,0,0,0,2,0,0,2,0,2,0,2,0,0,0,0,2,2,0,2,0,0,0,0,0,0,0,2,0,0,2,2,2,2,0,2},
  {2,2,2,2,2,0,0,0,2,2,0,2,0,0,0,0,2,0,2,0,2,0,0,2,2,0,2,2,0,2,2,2,2,0,0,0,0,0,0,0,0,0,2,0,0,0,0,2,0,2,0,0,0,0,2,0,0,0,0,0,0,0,0,0,2,2,2,2,0,2},
  {2,2,2,2,2,0,0,0,2,2,0,2,0,0,2,0,0,0,0,2,0,0,2,0,2,0,2,0,0,0,0,0,0,0,0,0,0,2,2,2,2,2,2,2,0,0,2,0,0,2,0,0,0,0,2,0,0,0,0,0,0,0,0,0,2,2,2,2,0,2},
  {2,0,0,0,2,0,0,0,2,2,0,2,0,0,0,0,0,0,2,0,0,0,2,0,2,0,0,0,2,0,0,0,0,0,0,0,2,2,2,2,0,0,2,0,2,0,2,2,0,2,0,0,0,0,2,0,0,2,0,2,0,2,0,0,2,2,2,2,0,2},
  {2,0,0,0,2,0,0,0,2,2,0,2,0,0,0,2,0,2,0,2,0,0,0,0,0,0,0,2,2,0,0,0,0,0,0,0,2,0,0,2,0,2,2,0,0,0,2,2,0,0,0,0,0,0,2,0,0,2,0,2,0,2,0,0,2,2,2,2,0,2},
  {2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2}};
#else
#ifdef MOUSEMAZE2
#define XSIZE 15
#define YSIZE 15
int maze[YSIZE][XSIZE] =
 {{2,2,2,2,2,2,2,2,2,2,2,2,2,2,2},
  {2,0,0,0,0,0,0,0,0,0,2,0,2,0,2},
  {2,0,2,0,2,0,2,0,2,0,0,0,2,0,2},
  {2,0,2,0,0,0,0,0,2,2,2,0,2,2,2},
  {2,0,2,0,2,0,2,0,2,2,0,0,2,0,2},
  {2,0,2,0,2,2,0,0,2,2,0,2,0,0,2},
  {2,0,0,0,2,2,0,0,0,2,0,2,2,0,2},
  {2,0,0,0,0,0,0,0,0,0,2,0,2,0,2},
  {2,0,2,0,2,0,2,0,2,0,0,0,2,0,2},
  {2,0,2,0,0,0,0,0,2,2,2,0,2,2,2},
  {2,0,2,0,2,0,2,0,2,2,0,0,2,0,2},
  {2,0,2,0,2,2,0,0,2,2,0,2,0,0,2},
  {2,0,0,0,2,2,0,0,0,2,0,2,2,0,2},
  {2,0,2,0,0,0,0,0,2,0,0,0,0,0,2},
  {2,2,2,2,2,2,2,2,2,2,2,2,2,2,2}};
#else
#define XSIZE 9
#define YSIZE 9
int maze[YSIZE][XSIZE] =
 {{2,2,2,2,2,2,2,2,2},
  {2,0,0,0,0,0,0,0,2},
  {2,0,2,0,2,0,2,0,2},
  {2,0,2,0,0,0,2,0,2},
  {2,0,2,0,2,0,2,0,2},
  {2,0,2,0,2,2,2,0,2},
  {2,0,2,0,2,2,2,0,2},
  {2,0,2,0,2,2,2,0,2},
  {2,2,2,2,2,2,2,2,2}};
#endif
#endif

int startx = 1, starty = 1;              /* 入口 */
int endx = XSIZE - 2, endy = YSIZE - 2;  /* 出口 */
const int top = 2;
const int left = 5;

long routes = 0;

#ifdef _WIN32
   #define WALLCODE 'X'

   HANDLE hOut;

   void gotoxy(int x, int y)
   {
    COORD pos;
    pos.X = x;
    pos.Y = y;
    SetConsoleCursorPosition(hOut, pos); /* 设置光标位置 */
   }
#else
   #define WALLCODE 219
#endif


int main(void)
{
 int i, j, k;

#ifdef _WIN32
   hOut = GetStdHandle(STD_OUTPUT_HANDLE);
#endif

 for (i = 0; i < YSIZE; i++)
  {
   for (j = 0; j < XSIZE; j++)
    {
     gotoxy(j + left, i + top);
     if (maze[i][j] == 2)
      printf("%c", WALLCODE);
     else
      printf(" ");
    }

   printf("\n");
  }
 gotoxy(startx + left, starty + top);
 printf("S");
 gotoxy(endx + left, endy + top);
 printf("E");

 getch();

 /* 多次搜索标记死角,直到找不到为止 */
 k = 1;
 while(k)
  {
   k = 0;
   for (i = starty; i <= endy; i++)
    {
     for (j = startx; j <= endx; j++)
      {
       if (maze[i][j] == 0 && (!(j == startx && i == starty)) && (!(j == endx && i == endy)))
        {
         if (maze[i - 1][j] != 0 && maze[i][j + 1] != 0 && maze[i + 1][j] != 0)
          {
           maze[i][j] = 3;
           k = 1;
           gotoxy(j + left, i + top);
           printf("%c", 'c');
          }
         else if (maze[i][j + 1] != 0 && maze[i + 1][j] != 0 && maze[i][j - 1] != 0)
          {
           maze[i][j] = 3;
           k = 1;
           gotoxy(j + left, i + top);
           printf("%c", 'c');
          }
         else if (maze[i + 1][j] != 0 && maze[i][j - 1] != 0 && maze[i - 1][j] != 0)
          {
           maze[i][j] = 3;
           k = 1;
           gotoxy(j + left, i + top);
           printf("%c", 'c');
          }
         else if (maze[i][j - 1] != 0 && maze[i - 1][j] != 0 && maze[i][j + 1] != 0)
          {
           maze[i][j] = 3;
           k = 1;
           gotoxy(j + left, i + top);
           printf("%c", 'c');
          }
        }
      }
    }
  }

 gotoxy(1, 1);
 getch();

 visit(startx, starty);
 printf("\n%ld", routes);

 getch();
}

void visit(int x, int y)
{
 maze[y][x] = 1;

 if (y == endy && x == endx)
  {
   gotoxy(1, 1);
   printf("%ld", ++routes);
  }

 if (maze[y + 1][x] == 0)
  visit(x, y + 1);
 if (maze[y][x + 1] == 0)
  visit(x + 1, y);
 if (maze[y - 1][x] == 0)
  visit(x, y - 1);
 if (maze[y][x - 1] == 0)
  visit(x - 1, y);

 maze[y][x] = 0;
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值