zoukankan      html  css  js  c++  java
  • [bfs][堆] Jzoj P5830 water

    Description

    有一块矩形土地被划分成 n*m 个正方形小块。这些小块高低不 平,每一小块都有自己的高度。水流可以由任意一块地流向周围四个 方向的四块地中,但是不能直接流入对角相连的小块中。 一场大雨后,由于地势高低不同,许多地方都积存了不少降水。 给定每个小块的高度,求每个小块的积水高度。 注意:假设矩形地外围无限大且高度为 0。
     

    Input

    第一行包含两个非负整数 n,m。 接下来 n 行每行 m 个整数表示第 i 行第 j 列的小块的高度。 

    Output

    输出 n 行,每行 m 个由空格隔开的非负整数,表示每个小块的积 水高度。 
     

    Sample Input

    3 3
    4 4 0
    2 1 3
    3 3 -1

    Sample Output

    0 0 0
    0 1 0
    0 0 1 
     

    Data Constraint

    对于 20%的数据 n,m<=4
    对于 40%的数据 n,m<=15
    对于 60%的数据 n,m<=50
    对于 100%的数据 n,m<=300,|小块高度|<=10^9。
    在每一部分数据中,均有一半数据保证小块高度非负

    题解

    • 首先,我们可以先将周围一圈的先加入小根堆,对于负数的,先将其定为0
    • 然后,bfs每次找到x四周第一个大于它的高度,那么小于它的就是加上h-a[x][y](x和y是当前四周搜到的高度,h为x的高度)
    • 以此类推

    代码

     1 #include <cstdio>
     2 #include <iostream>
     3 #include <queue>
     4 using namespace std;
     5 struct edge
     6 {
     7     int x,y;long long v;
     8     bool operator < (const edge &a) const { return v>a.v; }
     9 }u;
    10 priority_queue <edge> Q;
    11 int n,m,visit[310][310],dx[4]={0,0,1,-1},dy[4]={1,-1,0,0},a[310][310],h[310][310];
    12 bool pd(int x,int y)
    13 {
    14     if (x<1||x>n||y<1||y>m||visit[x][y]==1) return false;
    15     return true;
    16 }
    17 void work(int x,int y,int v)
    18 {
    19     visit[x][y]=1;
    20     if (a[x][y]>v) 
    21     {
    22         Q.push((edge){x,y,a[x][y]});
    23         return;
    24     }
    25     h[x][y]+=v-a[x][y];
    26     for (int i=0;i<=3;i++)    
    27         if (pd(x+dx[i],y+dy[i]))
    28             work(x+dx[i],y+dy[i],v);
    29 }
    30 void bfs()
    31 {
    32     while (!Q.empty())
    33     {
    34         u=Q.top(),Q.pop();
    35         for (int i=0;i<=3;i++)
    36             if (pd(u.x+dx[i],u.y+dy[i]))
    37                 work(u.x+dx[i],u.y+dy[i],u.v);
    38     }
    39 }
    40 int main()
    41 {
    42     //freopen("water.in","r",stdin);
    43     //freopen("water.out","w",stdout);
    44     scanf("%d%d",&n,&m);
    45     for (int i=1;i<=n;i++)
    46         for (int j=1;j<=m;j++)
    47         {
    48             scanf("%d",&a[i][j]);
    49             if (a[i][j]<0) h[i][j]=-a[i][j],a[i][j]=0;
    50             if (i==1||j==1||i==n||j==m) Q.push((edge){i,j,a[i][j]}),visit[i][j]=1;
    51         }
    52     bfs();
    53     for (int i=1;i<=n;i++)
    54     {
    55         for (int j=1;j<=m;j++) printf("%d ",h[i][j]);
    56         printf("
    ");
    57     }
    58     return 0;
    59 }
  • 相关阅读:
    程序数据集算地数据库
    使用属性升级mybank
    第一个C#程序
    CSS3动画
    定位网页元素的解析
    CSS3中的浮动
    CSS中的盒子模型
    (十三)mybatis 整合 ehcache
    (十二)mybatis 查询缓存
    (十一)延迟加载
  • 原文地址:https://www.cnblogs.com/Comfortable/p/9498353.html
Copyright © 2011-2022 走看看