hdu1072Nightmare(广搜)

题目链接:click~

题目解析:仍然是走过的点可以再走,所以标记数组vis[]记录的是经过该点的最大(而不是最小)的爆炸时间。

代码如下;

#include<cstdio>
#include<cstring>
#include<queue>
#include<iostream>
using namespace std;
int map[10][10];
int vis[10][10];
int m,n;
int begin_x,begin_y,end_x,end_y;
int dx[5]={0,0,1,-1};
int dy[5]={1,-1,0,0};
struct node
{
    int x;
    int y;
    int time;
    int bomb;
};
void bfs()
{
    memset(vis,0,sizeof(vis));
    node node1,node2;
    queue<node>q;
    node1.x=begin_x;
    node1.y=begin_y;
    node1.time=0;
    node1.bomb=6;
    q.push(node1);
    vis[node1.x][node1.y]=6;             //标记时注意走过的点任然可以再走,所以保存的是经过该点的最大爆炸时间
    while(!q.empty())
    {
        node2=q.front();
        //printf("%d %d %d %d-->\n",node2.x,node2.y,node2.time,node2.bomb);
        q.pop();
        if(node2.x==end_x&&node2.y==end_y)
        {
            printf("%d\n",node2.time);
            return ;
        }
        for(int i=0;i<4;i++)
        {
            node1.x=node2.x+dx[i];
            node1.y=node2.y+dy[i];
            if(node1.x>=1&&node1.x<=m&&node1.y>=1&&node1.y<=n)    //限制坐标
            {
                if(node2.bomb>=2)                                 //限制前一个点炸弹爆炸的时间
                {
                    if(map[node1.x][node1.y]==1||map[node1.x][node1.y]==3)
                    {
                        node1.time=node2.time+1;
                        node1.bomb=node2.bomb-1;
                        if(node1.bomb>vis[node1.x][node1.y])
                        {
                            q.push(node1);
                            vis[node1.x][node1.y]=node1.bomb;
                        }
                    }
                    if(map[node1.x][node1.y]==4)
                    {
                        node1.time=node2.time+1;
                        node1.bomb=6;
                        if(node1.bomb>vis[node1.x][node1.y])
                        {
                            q.push(node1);
                            vis[node1.x][node1.y]=node1.bomb;
                        }
                    }
                }
            }
        }
    }
    printf("-1\n");
}
int main()
{
    int T;
    scanf("%d",&T);
    while(T--)
    {
        scanf("%d%d",&m,&n);
        for(int i=1;i<=m;i++)
          for(int j=1;j<=n;j++)
          {
              scanf("%d",&map[i][j]);
              if(map[i][j]==2)
              {
                  begin_x=i;
                  begin_y=j;
              }
              if(map[i][j]==3)
              {
                  end_x=i;
                  end_y=j;
              }
          }
          bfs();
    }
    return 0;
}

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值