zoukankan      html  css  js  c++  java
  • 八百标兵奔北坡【DP】

    题目大意:

    对于一张地图上的点都有一个h[i][j]来表示这个地方的高度。现在一些人都想要跑到北边的一个山坡上。求出离每一个人最近的靠北的山。
    山:
    山的周围没有比它更高的地方。(四联通)
    在北边:
    令一个人的坐标为A(a,b),山的坐标为B(x,y) ,山在人的北边当且仅当dis[A][B]=ax
    Input

    5 5 5
    1 2 3 4 5
    2 3 4 5 1
    3 4 5 1 2
    4 5 1 2 3
    5 1 2 3 4
    1 2
    2 3
    3 4
    4 5
    5 1
    

    Output

    Pool Babingbaboom!
    Pool Babingbaboom!
    1
    2
    0

    思路:

    很明显是一道DP题目。
    画一下图就可以发现,其实在北边的位置就是一个三角形
    f[i][j]ij列距离北边最近山峰的距离。
    那么如果这个位置本身就是一个山峰,那么f[i][j]=0
    如果这个位置不是山峰,那么由于是一个三角形,就有

    f[i][j]=min(f[i1][j+1],min(f[i1][j1],f[i1][j]))+1

    采用离线算法,O(1)输出


    代码:

    #include <cstdio>
    #include <iostream>
    #include <cstring>
    #define Inf 99999999
    using namespace std;
    
    int n,m,k,x,y,a[2001][2001],f[2001][2001];
    
    int main()
    {
        scanf("%d%d%d",&n,&m,&k);
        memset(f,127/3,sizeof(f));  //初始化
        for (int i=1;i<=n;i++)
         for (int j=1;j<=m;j++)
          scanf("%d",&a[i][j]);
        for (int i=1;i<=n;i++)
         for (int j=1;j<=m;j++)  //枚举点
          f[i][j]=(a[i][j]<=a[i-1][j]||a[i][j]<=a[i+1][j]||a[i][j]<=a[i][j-1]||a[i][j]<=a[i][j+1])?min(f[i-1][j+1],min(f[i-1][j-1],f[i-1][j]))+1:0;  //若这是一个山峰,则f[i][j]=0,否则为旁边点到山峰的距离+1 
        while (k--)
        {
            scanf("%d%d",&x,&y);
            f[x][y]>Inf?printf("Pool Babingbaboom!\n"):printf("%d\n",f[x][y]);
        }
        return 0;
    }
  • 相关阅读:
    前端与算法 leetcode 344. 反转字符串
    JavaScript闭包使用姿势指南
    前端与算法 leetcode 48. 旋转图像
    前端与算法 leetcode 36. 有效的数独
    前端与算法 leetcode 1. 两数之和
    前端与算法 leetcode 283. 移动零
    前端与编译原理 用js去运行js代码 js2run
    前端与算法 leetcode 66. 加一
    前端与算法 leetcode 350. 两个数组的交集 II
    前端与算法 leetcode 26. 删除排序数组中的重复项
  • 原文地址:https://www.cnblogs.com/hello-tomorrow/p/11998836.html
Copyright © 2011-2022 走看看