UVALive - 3977 Summits (BFS染色)

题目大意:坑爹的题目,题意那么难理解。

讲的就是,如果该点是山顶的话(高度为h),那么以该点为中心,往外辐射,走高度大于h-d的点,到达不了另一个比它高的点

这就提示了,高度要从大到小排序,依次以高的点(假设高度为h)为核心辐射,如果碰上高度小于等于h-d的,表示此路不通了,就在该处停止

反之,如果碰上高度大于h-d的,且没有被染色过的,那么就将其染色

如果碰上高度大于h-d的,且被染色的话,就表明可以走到另一个更高点了,那么此点就不是山顶了

如果中途碰到了和该点一样高的,那么山顶的数量就加1

这里出现了失误,写代码的时候把M写成N了(定义数组的时候,本来是hight[M][M]的,结果写成了hight[N][N],这里N = 250010,M = 510),结果一直CE,很郁闷,但是电脑上的编译却过了

后来我把结构体的定义拉到了后面,在电脑上编译就出错了,空间不足

这就有点郁闷了,结构体的定义顺序还影响到了编译?

如果有大神知道的,还望告知一下

#include <cstdio>
#include <cstring>
#include <algorithm>
#include <queue>
using namespace std;
#define N 250010
#define M 510

struct Node {
    int x, y, h;
}node[N];

int dir[4][2] = {{-1, 0}, {1, 0}, {0, -1}, {0, 1}};
int Ans, H, W, D;
int color[M][M];
int hight[M][M];

bool cmp(const Node &a, const Node &b) {
    return a.h > b.h;
}

struct tmp_node{
    int x, y;
    tmp_node() {}
    tmp_node(int x, int y): x(x), y(y) {}
};

void bfs(int u) {
    bool flag = true;
    int tot = 1, lim = node[u].h - D, high = node[u].h;

    queue<tmp_node> Q;
    Q.push(tmp_node(node[u].x, node[u].y));
    color[node[u].x][node[u].y] = high;

    while (!Q.empty()) {
        tmp_node t = Q.front();
        Q.pop();
        for (int i = 0; i < 4; i++) {
            int x = t.x + dir[i][0];
            int y = t.y + dir[i][1];

            if (x >= H || x < 0 || y >= W || y < 0)
                continue;

            if (hight[x][y] <= lim)
                continue;
            if (color[x][y] != -1) {
                if (color[x][y] != high)
                    flag = false;
                continue;
            }

            if (color[x][y] == -1) {
                color[x][y] = high;
                Q.push(tmp_node(x,y));
            }
            if (hight[x][y] == high)
                tot++;
        }
    }
    if (flag)
        Ans += tot;
}

void solve() {
    sort(node, node + H * W, cmp);
    memset(color, -1, sizeof(color));
    Ans = 0;

    for (int i = 0; i < H * W; i++)
        if (color[node[i].x][node[i].y] == -1)
            bfs(i);
    printf("%d\n", Ans);
}

int main() {
    int test;
    scanf("%d", &test);
    while (test--) {

        scanf("%d%d%d", &H, &W, &D);
        for (int i = 0; i < H; i++)
            for (int j = 0; j < W; j++) {
                scanf("%d", &node[i * W + j].h);
                node[i * W + j].x = i;
                node[i * W + j].y = j;
                hight[i][j] = node[i * W + j].h;
            }
        solve();
    }
    return 0;
}

版权声明:本文为博主原创文章,未经博主允许不得转载。

时间: 2024-10-08 11:00:06

UVALive - 3977 Summits (BFS染色)的相关文章

UVALive 3977 BFS染色

这个题意搞了半天才搞明白 就是如果定义一个d-summit,即从该点到另一个更高的点,经过的路径必定是比当前点低至少d高度的,如果该点是最高点,没有比他更高的,就直接视为顶点 其实就是个BFS染色,先按降序排序,然后每个点对其可到达的点染色,h-d的点为边界,走到这里就不用往下染了 然后其他店染色的时候若产生冲突,则非d—summit,否则该点为顶点 今天还有COJ上一个BFS染色的题目,一直TLE...还没弄出来 #include <iostream> #include <cstdio

UVALive 6663 Count the Regions 离散+bfs染色_(:зゝ∠)_

题目链接:点击打开链接 gg..== #include <cstdio> #include <cstring> #include<iostream> #include <queue> #include <set> #include <map> #include <algorithm> #include <string> using namespace std; #define ll long long #def

XMU 1617 刘备闯三国之汉中之战 【BFS+染色】

1617: 刘备闯三国之汉中之战 Time Limit: 1000 MS  Memory Limit: 128 MBSubmit: 6  Solved: 5[Submit][Status][Web Board] Description 刘备(161年-223年6月10日),字玄德,东汉末年幽州涿郡涿县,西汉中山靖王刘胜的后代.刘备一生极具传奇色彩,早年颠沛流离.备尝艰辛最终却凭借自己的谋略终成一方霸主.那么在那个风云激荡的年代,刘备又是如何从一个卖草鞋的小人物一步一步成为蜀汉的开国皇帝呢?让我们

UVA 12130 - Summits(BFS+贪心)

UVA 12130 - Summits 题目链接 题意:给定一个h * w的图,每个位置有一个值,现在要求出这个图上的峰顶有多少个.峰顶是这样定义的,有一个d值,如果一个位置是峰顶,那么它不能走到不大于该峰顶高度 - d的位置,如果满足这个条件下,并且无法走到更高的山峰,那么它就是峰顶 思路:利用贪心的策略,把所有点丢到优先队列,每次取出最高的峰值开始找,进行广搜,搜的过程中记录下最大值的点的个数,如果这个是峰顶,就加上这个数.判断是不是峰顶的方法为,如果广搜过程中,不会找到一个点的能到的最高峰

UVA12130 Summits(BFS + 贪心)

UVA12130 Summits(BFS + 贪心) 题目链接 题目大意: 给你一个h ? w 的矩阵,矩阵的每个元素都有一个值,代表这个位置的高度.题目要求你找出这个图中有多少个位置是峰值点.从每个点(高度H)出发遍历这个图有一个要求,就是走过的点的高度不能小于等于H - d:成为峰值点的要求就是从这个点出发走到的位置不能有高度大于H的. 解题思路: 因为图很大,用dfs肯定不行.将这些点按照高度从大到小的排序,然后每个点作为起点来遍历,如果找到比这个点大的点就说明不是峰值点.并且遍历的过程中

UVALive 3977

直接搜索,简单题: #include<cstdio> #include<cstring> #include<cmath> #include<algorithm> #include<queue> #define maxn 505 #define ll long long using namespace std; int map[maxn][maxn]; int dir[4][2]={{0,1},{1,0},{0,-1},{-1,0}}; int v

BFS(染色) LA 3977 Summits

题目传送门 题意:题意坑爹.问符合条件的的山顶个数 分析:降序排序后从每个点出发,假设为山顶,如果四周的点的高度>h - d那么可以走,如果走到已经走过的点且染色信息(山顶高度)不匹配那么就不是山顶.重点在于就算知道不是山顶也要染色完. #include <bits/stdc++.h> using namespace std; const int N = 5e2 + 5; const int INF = 0x3f3f3f3f; int h, w, d; struct Point { in

uva 12130 - Summits(BFS)

题目链接:uva 12130 - Summits 题目大意:给定一个N?M的图,每个位置有一个值.给定D,表示有节点值为G的位置作为起点的话,将不能移动到值小于等于G?D的节点.现在要求找到整个图中所有的峰值点,峰值点的定义是不能移动到比自己节点值大的位置. 解题思路:将每个位置按照权值排序,逐个作为起点进行移动,v[x][y]数组值可以到达x,y的节点的值的最大值,如果起始点可以移动到v[x][y]大于本身的点,则说明该起点不是峰值点. #include <cstdio> #include

Hdu 5285 wyh2000 and pupil (bfs染色判断奇环) (二分图匹配)

题目链接: BestCoder Round #48 ($) 1002 题目描述: n个小朋友要被分成两班,但是有些小朋友之间是不认得的,所以规定不能把不认识的小朋友分在一个班级里面,并且一班的人数要比二班的人数多,每个班的人数都大于零. 解题思路: hdu给出的题解是二分图匹配加上贪心,就不多说了. 还可以用bfs对节点染色,建好图后,对节点进行bfs分成,偶数成与奇数成染成不同的颜色,颜色相同的节点都可以分到同一个集合里面,但是要判断一下奇环,如果出现奇环的话,是无法进行分组的.在每次bfs的