牛客练习赛12 B题

PS:
今天突然想打下这个比赛,结果好惨的,纪念下。。嘿嘿,反正第一道题我不会写。。。数学渣好菜。。。。

【题意】

求最短路径

【思路】

思路挺简单,求三遍某点到某点的最短的路径。
分别是S->E,S->K,K->E(需特判下门是否可以走)

【代码】

//bfs里方向的for循环造成数组越界,一直没找到问题所在,直到最后几分钟。。。简直了。。。
//不过突然发现代码结构有了进步,,,,估计是c#写多了。。。
#include<queue>
#include<cstdio>
#include<cmath>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn=500+10;
const int INF=1e9;
int n,m;
char arr[maxn][maxn];
struct pp
{
    int x,y;
} s,e,d,k;

bool vis[maxn][maxn];
int lestStep[maxn][maxn];
int dir[4][2]= {{-1,0},{1,0},{0,1},{0,-1}};
bool check(pp go,bool flag)
{
    if(!vis[go.x][go.y]&&go.x<=n&&go.x>0&&go.y<=m&&go.y>0&&arr[go.x][go.y]!='W')
    {
        if(!flag){
            if(arr[go.x][go.y]!='D')
            {
                return true;
            }
            return false;
        }
        return true;
    }
    return false;
}
int bfs(pp a,pp b,bool flag)
{
    memset(vis,0,sizeof(vis));
    memset(lestStep,0,sizeof(lestStep));
    queue<pp> que;
    que.push(a);
    vis[a.x][a.y]=true;
    while(!que.empty())
    {
        a=que.front();
        que.pop();
        if(a.x==b.x&&a.y==b.y)
        {
            return lestStep[b.x][b.y];
        }
        pp temp;
        for(int i=0; i<4; i++)
        {
            temp.x=a.x+dir[i][0];
            temp.y=a.y+dir[i][1];
            //printf("%d %d",temp.x,temp.y);
            //printf(" %c\n",arr[temp.x][temp.y]);
            if(check(temp,flag))
            {

                que.push(temp);
                lestStep[temp.x][temp.y]=lestStep[a.x][a.y]+1;
                vis[temp.x][temp.y]=true;
            }
        }
    }
    return INF;
}

int main()
{
    while(~scanf("%d%d",&n,&m))
    {
        for(int i=1; i<=n; i++)
        {
            scanf("%s",arr[i]+1);
            for(int j=1; j<=m; j++)
            {
                if(arr[i][j]=='S')
                {
                    s.x=i;
                    s.y=j;
                }
                else if(arr[i][j]=='E')
                {
                    e.x=i;
                    e.y=j;
                }
                else if(arr[i][j]=='D')
                {
                    d.x=i;
                    d.y=j;
                }
                else if(arr[i][j]=='K')
                {
                    k.x=i;
                    k.y=j;
                }
            }
        }
        int Lest_S_E=bfs(s,e,0);

        int Lest_S_K_D_E=bfs(s,k,0)+bfs(k,e,1);
        int res=min(Lest_S_E,Lest_S_K_D_E);
        if(res>=INF)
            printf("-1\n");
        else
            printf("%d\n",res);

    }

}
/*
4 12
WWWWWWWWWWWW
WE.W.S..W.KW
W..D..W....W
WWWWWWWWWWWW
*/
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值