zoukankan      html  css  js  c++  java
  • HDU 1728 逃离迷宫【BFS】

    题意:给出一个起点,一个终点,规定的转弯次数,问能否在规定的转弯次数内到达终点---

    这一题是学(看)习(题)的(解)@_@

    主要学了两个地方

    一个是剪枝,如果搜到的当前点的转弯次数小于该点turn数组记录下来的转弯次数,才有必要将它加入队列。

    另一个是记录转弯方向 在结构体里面定义一个turn来记录转弯的个数,用dir来记录当前所在的方向(因为搜的时候是四个方向dir[4][2]来搜的,直接用i确定当前方向即可)

    想想自己第一次做的时候的doubi想法,用dfs做,然后dfs(x,y,px,py),再判断由(x+dir[i][0],y+dir[i][1])与(x,y)构成的直线斜率和(x,y)和(px,py)构成的斜率乘积是否为-1-----果断没有写对----

     1 #include<iostream>  
     2 #include<cstdio>  
     3 #include<cstring>  
     4 #include<algorithm> 
     5 #include<queue> 
     6 using namespace std;
     7 int turn[105][105];
     8 int n,m,k;
     9 int dir[4][2]={{1,0},{-1,0},{0,1},{0,-1}};
    10 char map[105][105];
    11 struct node
    12 {
    13     int x,y;
    14     int turn,dir;//用turn来记录转弯的个数,用dir来记录当前的方向 
    15 } st,en,now,next;
    16 queue<node>q;
    17 void bfs()
    18 {
    19     while(!q.empty()) q.pop();
    20     now.x=st.x;now.y=st.y;now.dir=-5;now.turn=0;//初始的方向可以定义为任意一个后来不会出现的方向 
    21     turn[now.x][now.y]=0;    //在起点时可以转向任意方向,令为0 
    22     q.push(now);
    23     while(!q.empty())
    24     {
    25         now=q.front();q.pop();
    26     
    27         for(int i=0;i<4;i++)
    28         {
    29             next.x=now.x+dir[i][0];
    30             next.y=now.y+dir[i][1];
    31             next.dir=now.dir;
    32             next.turn=now.turn;
    33             if(now.x==en.x&&now.y==en.y&&now.turn<=k)
    34             {
    35             printf("yes
    ");
    36             return;            
    37             }
    38             if(next.x<1||next.x>m||next.y<1||next.y>n||map[next.x][next.y]=='*') continue;//第一次剪枝 
    39             if(next.dir!=i&&next.dir!=-5) //如果当前方向和起始不同,则turn++ 
    40                 next.turn++;
    41             if(next.turn>k) continue;//第二次剪 枝,转弯次数超过了,则剪枝 
    42             if(next.x==en.x&&next.y==en.y&&next.turn<=k)
    43             {
    44             printf("yes
    ");
    45             return;            
    46             }
    47             
    48             if(next.turn<=turn[next.x][next.y])//第三次剪枝,如果当前转弯的个数小于当前点的转弯个数,才有继续搜索的必要 
    49             {
    50                 next.dir=i;
    51                 turn[next.x][next.y]=next.turn;
    52                 q.push(next);
    53             }            
    54         }
    55     }
    56     printf("no
    ");
    57     return;    
    58 }
    59 int main()
    60 {
    61     int ncase,i,j;
    62     scanf("%d",&ncase);
    63     while(ncase--)
    64     {
    65         scanf("%d %d",&m,&n);
    66         for(i=1;i<=m;i++)
    67         for(j=1;j<=n;j++)
    68         {
    69             cin>>map[i][j];
    70             turn[i][j]=1000000;//初始化 每一点的转弯个数为一个极大的值 
    71         }
    72         cin>>k>>st.y>>st.x>>en.y>>en.x;
    73         bfs();
    74     }    
    75 }
    View Code
  • 相关阅读:
    程序设计实践读书笔记(一)
    Markdown语法和MWeb使用说明
    Comparable和Comparator的学习笔记
    WMware给centos6.8虚拟机添加硬盘
    Centos定时自动执行脚本
    linux开机关机自启动或自关闭服务的方式
    jira从windows迁移到linux
    ERROR: transport error 202:bind failed:Address already in use
    linux文件备份到windows方法
    validator验证
  • 原文地址:https://www.cnblogs.com/wuyuewoniu/p/4295746.html
Copyright © 2011-2022 走看看