zoukankan      html  css  js  c++  java
  • 引水入城 记忆化搜索

    引水入城 记忆化搜索

    题面

    注意问题本身的特殊性质来解决问题,注意到每个起点到最后一行的路线之间独立,容易想到一种方法:第一行所有点都跑一次dfs,然后标记一下最后一行是谁跑到的,最后问题转换为选取最少个区间覆盖整个区间的问题。

    考虑使用记忆化搜索优化。发现每一个起点覆盖最后一行的区间一定是连续的,所以可以用(l[i][j])表示第(i)(j)列可以到达最后一行的最左点。此题搜索是其实更多的像是在做dp。注意将最后一行初始化。

    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    #define MAXN 505
    using namespace std;
    bool vis[MAXN][MAXN];
    int mv[4][2]={{1,0},{-1,0},{0,1},{0,-1}};
    int n,m;
    int h[MAXN][MAXN];
    int l[MAXN][MAXN];
    int r[MAXN][MAXN];
    void dfs(int x, int y){
        vis[x][y]=1;
        for(int i=0;i<4;++i){
            int cx=x+mv[i][0],cy=y+mv[i][1];
            if(cx<1||cx>n||cy<1||cy>m) continue;
            if(h[cx][cy]>=h[x][y]) continue;
            if(!vis[cx][cy]) dfs(cx,cy);
            l[x][y]=min(l[x][y], l[cx][cy]);
            r[x][y]=max(r[x][y], r[cx][cy]);
        }
    }
    void solve(){
        for(int i=1;i<=m;++i)
            if(!vis[1][i]) dfs(1, i);
        int cnt=0;
        for(int i=1;i<=m;++i)
            if(!vis[n][i]) ++cnt;
        if(cnt!=0){
            printf("0
    %d", cnt);
            return;
        }
        int cur=1,ans=0;
        while(cur<=m){
            int mxr=0;
            for(int i=1;i<=m;++i)
                if(l[1][i]<=cur) mxr=max(mxr, r[1][i]);
            ++ans;
            cur=mxr+1;
        }
        printf("1
    %d", ans);
    }
    int main(){
        scanf("%d %d", &n, &m);
        for(int i=1;i<=n;++i)
            for(int j=1;j<=m;++j)
                scanf("%d", &h[i][j]);
        memset(vis, 0, sizeof(vis));
        memset(l, 0x3f, sizeof(l));
        memset(r, 0, sizeof(r));
        for (int i=1;i<=m;i++)
            l[n][i]=r[n][i]=i;
        solve();
    }
    
    
  • 相关阅读:
    【BZOJ5281】Talent Show(分数规划)
    数据库的连接(学习笔记)
    锁(学习笔记)
    事务处理(学习笔记)
    游标(学习笔记)
    PL/SQL基础-异常处理
    通用函数(学习笔记)
    转换函数(学习笔记)
    数据库的备份和恢复(学习笔记学习中)
    分析函数
  • 原文地址:https://www.cnblogs.com/santiego/p/11399786.html
Copyright © 2011-2022 走看看