zoukankan      html  css  js  c++  java
  • [ACM训练] 算法初级 之 搜索算法 之 深度优先算法DFS (POJ 2251+2488+3083+3009+1321)

    对于深度优先算法,第一个直观的想法是只要是要求输出最短情况的详细步骤的题目基本上都要使用深度优先来解决。比较常见的题目类型比如寻路等,可以结合相关的经典算法进行分析。

    常用步骤:


    第一道题目:Dungeon Master  http://poj.org/problem?id=2251

    Input

    The input consists of a number of dungeons. Each dungeon description starts with a line containing three integers L, R and C (all limited to 30 in size). 
    L is the number of levels making up the dungeon. 
    R and C are the number of rows and columns making up the plan of each level. 
    Then there will follow L blocks of R lines each containing C characters. Each character describes one cell of the dungeon. A cell full of rock is indicated by a '#' and empty cells are represented by a '.'. Your starting position is indicated by 'S' and the exit by the letter 'E'. There's a single blank line after each level. Input is terminated by three zeroes for L, R and C.

    Output

    Each maze generates one line of output. If it is possible to reach the exit, print a line of the form 
    Escaped in x minute(s).

    where x is replaced by the shortest time it takes to escape. 
    If it is not possible to escape, print the line 
    Trapped!

    Sample Input

    3 4 5
    S....
    .###.
    .##..
    ###.#
    
    #####
    #####
    ##.##
    ##...
    
    #####
    #####
    #.###
    ####E
    
    1 3 3
    S##
    #E#
    ###
    
    0 0 0

    此题目只要求了求出最短的路径步骤,肯定适合使用广度优先算法来处理,但是如果再要求输出对应最短路径下的具体路径,则只能使用深度优先来处理了。

    先来一个广度优先算法的参考代码:

      1 #include <iostream>
      2 #include <cstdio>
      3 #include <queue>
      4 #include <cmath>
      5 #include <cstring>
      6 
      7 using namespace std;
      8 
      9 int l,r,c;
     10 
     11 struct node
     12 {
     13     int i;
     14     int j;
     15     int k;
     16     int s;
     17 };
     18 
     19 string road[30][30];
     20 int visited[30*30*30];//i*r*c+j*c+k为索引值
     21 
     22 void getroad(int es)
     23 {
     24     int i,j,k;
     25     node first,next;
     26     bool flag=false;
     27 
     28     for(i=0;i<l;i++)
     29     {
     30         for(j=0;j<r;j++)
     31         {
     32             for(k=0;k<c;k++)
     33             {
     34                 if(road[i][j][k] == 'S')//找到初始点,标记
     35                 {
     36                     first.i=i;
     37                     first.j=j;
     38                     first.k=k;
     39                     first.s=0;
     40                     flag=true;
     41                     break;
     42                 }
     43             }
     44             if(flag)
     45                 break;
     46         }
     47         if(flag)
     48             break;
     49     }
     50 
     51     queue<node> q;
     52     q.push(first);
     53     visited[first.i*r*c+first.j*c+first.k]=es;
     54 
     55     while(!q.empty())
     56     {
     57         first=q.front();
     58         q.pop();
     59 
     60         //需要设计上下左右前后6个方向,1维只有上下j左右k,2维以上再添加前后i
     61         //同时需要考虑是否处在边界的情况
     62         next=first;
     63         next.s+=1;
     64         int index=0;
     65 
     66         next.j-=1;//
     67         index=next.i*r*c+next.j*c+next.k;
     68         if(next.j>=0 && road[next.i][next.j][next.k] == '.')
     69         {
     70             if(visited[index] != es)
     71             {
     72                 q.push(next);
     73                 visited[index]=es;
     74             }
     75         }
     76         if(next.j>=0 && road[next.i][next.j][next.k] == 'E')
     77         {
     78             cout<<"Escaped in "<<next.s<<" minute(s)."<<endl;
     79             return;
     80         }
     81 
     82         next.j+=2;//
     83         index=next.i*r*c+next.j*c+next.k;
     84         //cout<<str[next.i][next.j][next.k]<<endl;
     85         if(next.j<r && road[next.i][next.j][next.k] == '.')
     86         {
     87             if(visited[index] != es)
     88             {
     89                 q.push(next);
     90                 visited[index]=es;
     91             }
     92         }
     93         if(next.j<r && road[next.i][next.j][next.k] == 'E')
     94         {
     95             cout<<"Escaped in "<<next.s<<" minute(s)."<<endl;
     96             return;
     97         }
     98 
     99         next.j-=1;//复原
    100 
    101         next.k-=1;//
    102         index=next.i*r*c+next.j*c+next.k;
    103         if(next.k>=0 && road[next.i][next.j][next.k] == '.')
    104         {
    105             if(visited[index] != es)
    106             {
    107                 q.push(next);
    108                 visited[index]=es;
    109             }
    110         }
    111         if(next.k>=0 && road[next.i][next.j][next.k] == 'E')
    112         {
    113             cout<<"Escaped in "<<next.s<<" minute(s)."<<endl;
    114             return;
    115         }
    116 
    117         next.k+=2;//
    118         index=next.i*r*c+next.j*c+next.k;
    119         if(next.k<c && road[next.i][next.j][next.k] == '.')
    120         {
    121             if(visited[index] != es)
    122             {
    123                 q.push(next);
    124                 visited[index]=es;
    125             }
    126         }
    127         if(next.k<c && road[next.i][next.j][next.k] == 'E')
    128         {
    129             cout<<"Escaped in "<<next.s<<" minute(s)."<<endl;
    130             return;
    131         }
    132 
    133         next.k-=1;//复原
    134 
    135         if(l>1)
    136         {
    137             next.i-=1;//
    138             index=next.i*r*c+next.j*c+next.k;
    139             if(next.i>=0 && road[next.i][next.j][next.k] == '.')
    140             {
    141                 if(visited[index] != es)
    142                 {
    143                     q.push(next);
    144                     visited[index]=es;
    145                 }
    146             }
    147             if(next.i>=0 && road[next.i][next.j][next.k] == 'E')
    148             {
    149                 cout<<"Escaped in "<<next.s<<" minute(s)."<<endl;
    150                 return;
    151             }
    152 
    153             next.i+=2;//
    154             index=next.i*r*c+next.j*c+next.k;
    155             if(next.i<l && road[next.i][next.j][next.k] == '.')
    156             {
    157                 if(visited[index] != es)
    158                 {
    159                     q.push(next);
    160                     visited[index]=es;
    161                 }
    162             }
    163             if(next.i<l && road[next.i][next.j][next.k] == 'E')
    164             {
    165                 cout<<"Escaped in "<<next.s<<" minute(s)."<<endl;
    166                 return;
    167             }
    168         }
    169     }
    170     cout<<"Trapped!"<<endl;
    171 }
    172 
    173 
    174 int main()
    175 {
    176     int count=1;
    177 
    178     while(true)
    179     {
    180         cin>>l>>r>>c;
    181 
    182         if(l==0 && r==0 && c==0)
    183             break;
    184 
    185 
    186         int i=0;
    187         int j=0;
    188         string tmp;
    189         for(i=0;i<l;i++)
    190         {
    191             for(j=0;j<r;j++)
    192                 cin>>road[i][j];
    193             getline(cin,tmp);
    194         }
    195         getroad(count);
    196 
    197         for(i=0;i<l;i++)
    198             for(j=0;j<r;j++)
    199                 road[i][j].clear();
    200 
    201         count++;
    202     }
    203 
    204     return 0;
    205 }
    View Code

    题目更改一下,要求输出最短步数,并且输出对应的具体路径。

    考虑一下:

  • 相关阅读:
    Go反射
    Go_CSP并发模型
    Go_select
    Go计时器
    day9:vcp考试
    day8:vcp考试
    day7:vcp考试
    day6:vcp考试
    day5:vcp考试
    day4:vcp考试
  • 原文地址:https://www.cnblogs.com/yushuo1990/p/5991760.html
Copyright © 2011-2022 走看看