• dp+bfs Buggy Robot


    题目链接:https://nanti.jisuanke.com/t/40891

    题意:

    给你一个地图,机器人从起点到终点按照字符串的指示前进,如果遇到障碍或者出边界就停留在原地,不算违规。

    问你最少修改字符串的几个字符,才能让机器人到终点。

    分析:

    用dp[i][j][k]表示扫描完前k个字符之后,到达地图坐标(i,j)上的最小代价。

    把每个状态都依次穷举,加入队列后bfs。

    #include<bits/stdc++.h>
    using namespace std;
    const int inf=0x3f3f3f3f;
    #define mem0(a) memset(a,0,sizeof(a))
    #define meminf(a) memset(a,0x3f,sizeof(a))
    const int maxn=1e5+10;
    char s[60][60],pre[60];
    int dp[60][60][60];
    int h,w;
    struct node{
        int x,y,pos;
        node(int x,int y,int pos):x(x),y(y),pos(pos){}
    };
    queue<node> q;
    bool check(int x,int y){
        return x>0&&x<=h&&y>0&&y<=w&&s[x][y]!='#';
    }
    int main(){
        scanf("%d%d",&h,&w);
        int sx,sy,gx,gy;
        for(int i=1;i<=h;i++){
            scanf("%s",s[i]+1);
            for(int j=1;j<=w;j++){
                if(s[i][j]=='S') sx=i,sy=j;
                if(s[i][j]=='G') gx=i,gy=j;
            }
        }
        scanf("%s",pre+1);
        int len=strlen(pre+1);
        int nxt[4][2]={{0,1},{0,-1},{-1,0},{1,0}}; 
        int m['Z'+1];
        m['R']=0;m['L']=1;m['U']=2;m['D']=3;
        meminf(dp);
        dp[sx][sy][0]=0;
        q.push(node(sx,sy,0));
        while(!q.empty()){
            node now=q.front();q.pop();
            for(int i=0;i<4;i++){
                //在pos位置处添加一个指令 
                int nowx=now.x+nxt[i][0],nowy=now.y+nxt[i][1];
                if(check(nowx,nowy))
                if(dp[nowx][nowy][now.pos]>dp[now.x][now.y][now.pos]+1){
                    dp[nowx][nowy][now.pos]=dp[now.x][now.y][now.pos]+1;
                    q.push(node(nowx,nowy,now.pos));
                }
            }
            if(now.pos<len){
                //在pos位置处删除一个指令 
                if(dp[now.x][now.y][now.pos+1]>dp[now.x][now.y][now.pos]+1){
                    dp[now.x][now.y][now.pos+1]=dp[now.x][now.y][now.pos]+1;
                    q.push(node(now.x,now.y,now.pos+1));
                }
                //按照初始指令来行进 
                int pos=now.pos+1;//扫描下一个 
                int nowx=now.x+nxt[m[pre[pos]]][0],nowy=now.y+nxt[m[pre[pos]]][1];
            //    cout<<" "<<nowx<<" "<<nowy<<endl;
                if(!check(nowx,nowy)) nowx=now.x,nowy=now.y;
                if(dp[nowx][nowy][now.pos+1]>dp[now.x][now.y][now.pos]){
                    //前者可以由后者自然转换来,如果后者代价更低是可以直接变更的
                     dp[nowx][nowy][now.pos+1]=dp[now.x][now.y][now.pos];
                     q.push(node(nowx,nowy,now.pos+1));
                } 
            }
        }
        int ans=inf;
        for(int i=0;i<=len;i++) ans=min(ans,dp[gx][gy][i]);
        cout<<ans<<endl;
        return 0;
    }
  • 相关阅读:
    学习:HelloWorld项目目录
    学习:java设计模式—Adapter模式
    学习:java设计模式—Decorator模式
    MyEclipse8.5/8.6不能安装ADT
    学习:Android框架
    笔记:代码整洁之道
    JVM常用启动参数
    春雷第一声初入博客
    在Winform中更改控件导致designer中代码自动移除解决方法
    C#生成灰度图片:拖动图片到picturebox显示,拖动picturebox图片到资源管理器 (Drag & drop )
  • 原文地址:https://www.cnblogs.com/qingjiuling/p/11356696.html
Copyright © 2020-2023  润新知