zoukankan      html  css  js  c++  java
  • POJ3083Children of the Candy Corn

    题意:给你一个迷宫,入口处标为S,出口处标为E,可以走的地方为“.”,不可以走的地方为#,求左转优先时从出口到入口的路程,再求右转优先时,出口到入口的路程,最后求从出口到入口的最短路程。

    思路:求前两个的时候用DFS递归求解能走的路就OK,求最短的时候当然要用广度优先搜索啦。

      1 #include<cstdio>
      2 #include<cstring>
      3 #include<iostream>
      4 using namespace std ;
      5 char ch[158][158];
      6 int sum ;//总步数
      7 int h,w,i,j,k ;
      8 int enx,eny,stax,stay;
      9 int fx[] = {0,1,0,-1};//列的变化,从0开始顺时针变化
     10 int fy[] = {1,0,-1,0};//行的变化,从0开始顺时针变化
     11 int lef[] = {1,0,3,2};//左转优先时,标记上下左右4个方向分别为0213;
     12 int rig[] = {3,0,1,2};//右转优先时,右边为1;
     13 struct node
     14 {
     15     int xz,yz;
     16     int cnt;
     17 } sh[10001];//数组模拟队列
     18 void DFS(int dire,int x,int y,int d)//这个点的初始方向,这个点现在坐标,以及是左先还是右先
     19 {
     20     if(x == enx&&y == eny)//如果遍历到了'E'所在坐标,就结束掉遍历,返回
     21     {
     22         printf("%d",sum);
     23         return ;
     24     }
     25     int xx,yy;
     26     sum++;
     27     if(d == 1)//左转优先
     28     {
     29         for(i = 0 ; i <= 3 ; i++)//4个方向遍历一遍
     30         {
     31             j = (dire+lef[i])%4;//求出当前位置的方向数字
     32             xx = x+fx[j];//传过来的参数x为原来的坐标j
     33             yy = y+fy[j];
     34             if(xx>=0&&xx< h&&yy>=0&&yy< w&&ch[yy][xx] != '#')//继续遍历的条件是不为#且没越出边界,要注意xx是到h为边界的与主函数中对应
     35             {
     36                 DFS(j,xx,yy,1);//继续递归下去
     37                 return ;
     38             }
     39         }
     40     }
     41     else
     42     {
     43         for(i = 0 ; i <= 3 ; i++)
     44         {
     45             j = (dire+rig[i])%4;
     46             xx = x+fx[j];
     47             yy = y+fy[j];
     48             if(xx>=0 && xx < h&&yy>=0 && yy < w&&ch[yy][xx] != '#')
     49             {
     50                 DFS(j,xx,yy,0);
     51                 return ;
     52             }
     53         }
     54     }
     55 }
     56 void BFS(int x,int y)//广度优先搜索是队列,深度优先搜索是栈,深度是递归
     57 {
     58     int zh[158][158] = {0};//标记数组,初始化为0,表示节点未被访问过
     59     int le = 0,ri = 1 ;
     60     zh[y][x] = 1;
     61     //将当前点坐标压入队列,后边进行处理
     62     sh[0].xz = x;
     63     sh[0].yz = y ;
     64     sh[0].cnt = 1 ;
     65     while(le < ri)
     66     {
     67         x = sh[le].xz;//从队列中取出进行操作
     68         y = sh[le].yz ;
     69         sum = sh[le++].cnt;
     70         for(k = 0 ; k <= 3 ; k++)
     71         {
     72             //点的坐标
     73             i = y+fy[k];
     74             j = x+fx[k];
     75             if(i>=0 && i<w && j<h && j>=0 && !zh[i][j] &&ch[i][j]!='#')//在原有条件下,还要保证节点没有被访问过
     76             {
     77                 if(j == enx&&i == eny)//如果找到'E'就输出长度
     78                 {
     79                     cout<<sum+1<<endl;
     80                     return ;
     81                 }
     82                 zh[i][j] = 1;//表示这个节点已经被访问过了,标记为1
     83                 //将这个点加入队列用来以后进行访问这个点四周的点
     84                 sh[ri].yz = i;
     85                 sh[ri].xz = j;
     86                 sh[ri].cnt = sum+1;//这个点步数加1
     87                 ri++;//while循环结束的条件就是该点不符合条件,ri不再累加
     88             }
     89         }
     90     }
     91 }
     92 int main()
     93 {
     94     int n,dire;
     95     scanf("%d",&n);
     96     while(n--)
     97     {
     98         scanf("%d %d",&h,&w);//h是列,w是行
     99         for(i = 0 ; i <= w-1 ; i++)
    100         {
    101             scanf("%s",ch[i]);
    102             for(j = 0 ; j <= h-1 ; j++)
    103             {
    104                 if(ch[i][j] == 'S')
    105                 {
    106                     stax = j;
    107                     stay = i;
    108                 }
    109                 if(ch[i][j] == 'E')
    110                 {
    111                     enx = j;
    112                     eny = i ;
    113                 }
    114             }
    115         }
    116         if(stax == 0) dire = 1;//
    117         if(stax == h-1) dire = 3;//
    118         if(stay == 0) dire = 0;//
    119         if(stay == w-1) dire = 2 ;//
    120         sum = 1;//初始化
    121         DFS(dire,stax,stay,1);//左转优先
    122         printf(" ");
    123         sum = 1 ;//初始化
    124         DFS(dire,stax,stay,0);//右转优先
    125         printf(" ");
    126         BFS(stax,stay);//求最短的用bfs
    127     }
    128     return 0;
    129 }
    View Code
  • 相关阅读:
    ASP.NET MVC随想录——锋利的KATANA
    ASP.NET MVC随想录——漫谈OWIN
    Notepad++ 64位 插件管理
    C#实现按键精灵的'找图' '找色' '找字'的功能
    http://www.haolizi.net/example/view_2380.html
    C# 关于在原图中寻找子图片坐标的类
    WebBrowser控件默认使用IE9,IE10的方法
    Springboot---后台导出功能,easyExcel
    vue---EleElement UI 表格导出功能
    vue---提取公共方法
  • 原文地址:https://www.cnblogs.com/luyingfeng/p/3254722.html
Copyright © 2011-2022 走看看